diff --git a/.specstory/history/2026-03-13_20-29Z-retargeting-focus-object-issue.md b/.specstory/history/2026-03-13_20-29Z-retargeting-focus-object-issue.md
index a6b29de..4735fd5 100644
--- a/.specstory/history/2026-03-13_20-29Z-retargeting-focus-object-issue.md
+++ b/.specstory/history/2026-03-13_20-29Z-retargeting-focus-object-issue.md
@@ -1648,3 +1648,284 @@ The search didn't give me the exact API for selecting bones in pose mode. Let me
---
+Thought Process
+This is very helpful. It says that in Blender 5.0, bone selection state is now stored on the **pose bone** itself rather than on the bone data. So instead of `rep.data.bones[name].select_head`, we should use the pose bone directly.
+
+Let me search for more specific information about how to select bones via the pose bone.
+
+---
+
+
+
+Tool use: **web_fetch**
+
+
+Parameters:
+
+```json
+{
+ "url": "https://docs.blender.org/api/current/bpy.types.PoseBone.html"
+}
+```
+Result:
+
+```json
+{
+ "url": "https://docs.blender.org/api/current/bpy.types.PoseBone.html",
+ "markdown": "PoseBone(bpy_struct) - Blender Python API\n\n# PoseBone(bpy_struct)¶\n\nbase class — [bpy_struct](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct)\n\nclass bpy.types.PoseBone(bpy_struct)¶\n\nChannel defining pose data for a bone in a Pose\n\nbbone_curveinx¶\n\nX-axis handle offset for start of the B-Bone’s curve, adjusts curvature\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_curveinz¶\n\nZ-axis handle offset for start of the B-Bone’s curve, adjusts curvature\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_curveoutx¶\n\nX-axis handle offset for end of the B-Bone’s curve, adjusts curvature\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_curveoutz¶\n\nZ-axis handle offset for end of the B-Bone’s curve, adjusts curvature\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_custom_handle_end¶\n\nBone that serves as the end handle for the B-Bone curve\n\nType:\n\n`PoseBone`, (readonly)\n\nbbone_custom_handle_start¶\n\nBone that serves as the start handle for the B-Bone curve\n\nType:\n\n`PoseBone`, (readonly)\n\nbbone_easein¶\n\nLength of first Bézier Handle (for B-Bones only)\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_easeout¶\n\nLength of second Bézier Handle (for B-Bones only)\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_rollin¶\n\nRoll offset for the start of the B-Bone, adjusts twist\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_rollout¶\n\nRoll offset for the end of the B-Bone, adjusts twist\n\nType:\n\nfloat in [-inf, inf], default 0.0\n\nbbone_scalein¶\n\nScale factors for the start of the B-Bone, adjusts thickness (for tapering effects)\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (1.0, 1.0, 1.0)\n\nbbone_scaleout¶\n\nScale factors for the end of the B-Bone, adjusts thickness (for tapering effects)\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (1.0, 1.0, 1.0)\n\nbone¶\n\nBone associated with this PoseBone\n\nType:\n\n[Bone](https://docs.blender.org/api/current/bpy.types.Bone.html#bpy.types.Bone), (readonly, never None)\n\nchild¶\n\nChild of this pose bone\n\nType:\n\n`PoseBone`, (readonly)\n\ncolor¶ Type:\n\n[BoneColor](https://docs.blender.org/api/current/bpy.types.BoneColor.html#bpy.types.BoneColor), (readonly)\n\nconstraints¶\n\nConstraints that act on this pose channel\n\nType:\n\n[PoseBoneConstraints](https://docs.blender.org/api/current/bpy.types.PoseBoneConstraints.html#bpy.types.PoseBoneConstraints) [bpy_prop_collection](https://docs.blender.org/api/current/bpy.types.bpy_prop_collection.html#bpy.types.bpy_prop_collection) of [Constraint](https://docs.blender.org/api/current/bpy.types.Constraint.html#bpy.types.Constraint), (readonly)\n\ncustom_shape¶\n\nObject that defines custom display shape for this bone\n\nType:\n\n[Object](https://docs.blender.org/api/current/bpy.types.Object.html#bpy.types.Object)\n\ncustom_shape_rotation_euler¶\n\nAdjust the rotation of the custom shape\n\nType:\n\n[mathutils.Euler](https://docs.blender.org/api/current/mathutils.html#mathutils.Euler) rotation of 3 items in [-inf, inf], default (0.0, 0.0, 0.0)\n\ncustom_shape_scale_xyz¶\n\nAdjust the size of the custom shape\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (1.0, 1.0, 1.0)\n\ncustom_shape_transform¶\n\nBone that defines the display transform of this custom shape\n\nType:\n\n`PoseBone`\n\ncustom_shape_translation¶\n\nAdjust the location of the custom shape\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (0.0, 0.0, 0.0)\n\ncustom_shape_wire_width¶\n\nAdjust the line thickness of custom shapes\n\nType:\n\nfloat in [1, 16], default 0.0\n\nhead¶\n\nLocation of head of the channel’s bone\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (0.0, 0.0, 0.0), (readonly)\n\nhide¶\n\nBone is not visible except for Edit Mode\n\nType:\n\nboolean, default False\n\nik_linear_weight¶\n\nWeight of scale constraint for IK\n\nType:\n\nfloat in [0, 1], default 0.0\n\nik_max_x¶\n\nMaximum angles for IK Limit\n\nType:\n\nfloat in [0, 3.14159], default 0.0\n\nik_max_y¶\n\nMaximum angles for IK Limit\n\nType:\n\nfloat in [0, 3.14159], default 0.0\n\nik_max_z¶\n\nMaximum angles for IK Limit\n\nType:\n\nfloat in [0, 3.14159], default 0.0\n\nik_min_x¶\n\nMinimum angles for IK Limit\n\nType:\n\nfloat in [-3.14159, 0], default 0.0\n\nik_min_y¶\n\nMinimum angles for IK Limit\n\nType:\n\nfloat in [-3.14159, 0], default 0.0\n\nik_min_z¶\n\nMinimum angles for IK Limit\n\nType:\n\nfloat in [-3.14159, 0], default 0.0\n\nik_rotation_weight¶\n\nWeight of rotation constraint for IK\n\nType:\n\nfloat in [0, 1], default 0.0\n\nik_stiffness_x¶\n\nIK stiffness around the X axis\n\nType:\n\nfloat in [0, 0.99], default 0.0\n\nik_stiffness_y¶\n\nIK stiffness around the Y axis\n\nType:\n\nfloat in [0, 0.99], default 0.0\n\nik_stiffness_z¶\n\nIK stiffness around the Z axis\n\nType:\n\nfloat in [0, 0.99], default 0.0\n\nik_stretch¶\n\nAllow scaling of the bone for IK\n\nType:\n\nfloat in [0, 1], default 0.0\n\nis_in_ik_chain¶\n\nIs part of an IK chain\n\nType:\n\nboolean, default False, (readonly)\n\nlength¶\n\nLength of the bone\n\nType:\n\nfloat in [-inf, inf], default 0.0, (readonly)\n\nlocation¶ Type:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (0.0, 0.0, 0.0)\n\nlock_ik_x¶\n\nDisallow movement around the X axis\n\nType:\n\nboolean, default False\n\nlock_ik_y¶\n\nDisallow movement around the Y axis\n\nType:\n\nboolean, default False\n\nlock_ik_z¶\n\nDisallow movement around the Z axis\n\nType:\n\nboolean, default False\n\nlock_location¶\n\nLock editing of location when transforming\n\nType:\n\nboolean array of 3 items, default (False, False, False)\n\nlock_rotation¶\n\nLock editing of rotation when transforming\n\nType:\n\nboolean array of 3 items, default (False, False, False)\n\nlock_rotation_w¶\n\nLock editing of ‘angle’ component of four-component rotations when transforming\n\nType:\n\nboolean, default False\n\nlock_rotations_4d¶\n\nLock editing of four component rotations by components (instead of as Eulers)\n\nType:\n\nboolean, default False\n\nlock_scale¶\n\nLock editing of scale when transforming\n\nType:\n\nboolean array of 3 items, default (False, False, False)\n\nmatrix¶\n\nFinal 4×4 matrix after constraints and drivers are applied, in the armature object space\n\nType:\n\n[mathutils.Matrix](https://docs.blender.org/api/current/mathutils.html#mathutils.Matrix) of 4 * 4 items in [-inf, inf], default ((0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0))\n\nmatrix_basis¶\n\nAlternative access to location/scale/rotation relative to the parent and own rest bone\n\nType:\n\n[mathutils.Matrix](https://docs.blender.org/api/current/mathutils.html#mathutils.Matrix) of 4 * 4 items in [-inf, inf], default ((0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0))\n\nmatrix_channel¶\n\n4×4 matrix of the bone’s location/rotation/scale channels (including animation and drivers) and the effect of bone constraints\n\nType:\n\n[mathutils.Matrix](https://docs.blender.org/api/current/mathutils.html#mathutils.Matrix) of 4 * 4 items in [-inf, inf], default ((0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0), (0.0, 0.0, 0.0, 0.0)), (readonly)\n\nmotion_path¶\n\nMotion Path for this element\n\nType:\n\n[MotionPath](https://docs.blender.org/api/current/bpy.types.MotionPath.html#bpy.types.MotionPath), (readonly)\n\nname¶ Type:\n\nstring, default “”, (never None)\n\nparent¶\n\nParent of this pose bone\n\nType:\n\n`PoseBone`, (readonly)\n\nrotation_axis_angle¶\n\nAngle of Rotation for Axis-Angle rotation representation\n\nType:\n\nfloat array of 4 items in [-inf, inf], default (0.0, 0.0, 1.0, 0.0)\n\nrotation_euler¶\n\nRotation in Eulers\n\nType:\n\n[mathutils.Euler](https://docs.blender.org/api/current/mathutils.html#mathutils.Euler) rotation of 3 items in [-inf, inf], default (0.0, 0.0, 0.0)\n\nrotation_mode¶\n\nThe kind of rotation to apply, values from other rotation modes are not used\n\nType:\n\nenum in [Object Rotation Mode Items](https://docs.blender.org/api/current/bpy_types_enum_items/object_rotation_mode_items.html#rna-enum-object-rotation-mode-items), default`'QUATERNION'`\n\nrotation_quaternion¶\n\nRotation in Quaternions\n\nType:\n\n[mathutils.Quaternion](https://docs.blender.org/api/current/mathutils.html#mathutils.Quaternion) rotation of 4 items in [-inf, inf], default (1.0, 0.0, 0.0, 0.0)\n\nscale¶ Type:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (1.0, 1.0, 1.0)\n\nselect¶\n\nBone is selected in Pose Mode\n\nType:\n\nboolean, default False\n\ntail¶\n\nLocation of tail of the channel’s bone\n\nType:\n\n[mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], default (0.0, 0.0, 0.0), (readonly)\n\nuse_custom_shape_bone_size¶\n\nScale the custom object by the bone length\n\nType:\n\nboolean, default False\n\nuse_ik_limit_x¶\n\nLimit movement around the X axis\n\nType:\n\nboolean, default False\n\nuse_ik_limit_y¶\n\nLimit movement around the Y axis\n\nType:\n\nboolean, default False\n\nuse_ik_limit_z¶\n\nLimit movement around the Z axis\n\nType:\n\nboolean, default False\n\nuse_ik_linear_control¶\n\nApply channel size as IK constraint if stretching is enabled\n\nType:\n\nboolean, default False\n\nuse_ik_rotation_control¶\n\nApply channel rotation as IK constraint\n\nType:\n\nboolean, default False\n\nuse_transform_around_custom_shape¶\n\nTransform the bone as if it was a child of the Custom Shape Transform bone. This can be useful when combining shape-key and armature deformations.\n\nType:\n\nboolean, default False\n\nuse_transform_at_custom_shape¶\n\nThe location and orientation of the Custom Shape Transform bone will be used for transform gizmos and for other transform operators in the 3D Viewport. When disabled, the 3D Viewport will still use the actual bone transform for these, even when the custom bone shape transform is overridden.\n\nType:\n\nboolean, default False\n\nbasename¶\n\nThe name of this bone before any`.` character.\n\n(readonly)\n\ncenter¶\n\nThe midpoint between the head and the tail.\n\n(readonly)\n\nchildren¶\n\n(readonly)\n\nchildren_recursive¶\n\nA list of all children from this bone.\n\nNote\n\nTakes`O(len(bones)**2)` time.\n\n(readonly)\n\nchildren_recursive_basename¶\n\nReturns a chain of children with the same base name as this bone. Only direct chains are supported, forks caused by multiple children with matching base names will terminate the function and not be returned.\n\nNote\n\nTakes`O(len(bones)**2)` time.\n\n(readonly)\n\nparent_recursive¶\n\nA list of parents, starting with the immediate parent.\n\n(readonly)\n\nvector¶\n\nThe direction this bone is pointing. Utility function for (tail - head)\n\n(readonly)\n\nx_axis¶\n\nVector pointing down the x-axis of the bone.\n\n(readonly)\n\ny_axis¶\n\nVector pointing down the y-axis of the bone.\n\n(readonly)\n\nz_axis¶\n\nVector pointing down the z-axis of the bone.\n\n(readonly)\n\nbl_system_properties_get(*, do_create=False)¶\n\nDEBUG ONLY. Internal access to runtime-defined RNA data storage, intended solely for testing and debugging purposes. Do not access it in regular scripting work, and in particular, do not assume that it contains writable data\n\nParameters:\n\ndo_create (boolean, (optional)) – Ensure that system properties are created if they do not exist yet\n\nReturns:\n\nThe system properties root container, or None if there are no system properties stored in this data yet, and its creation was not requested\n\nReturn type:\n\n[PropertyGroup](https://docs.blender.org/api/current/bpy.types.PropertyGroup.html#bpy.types.PropertyGroup)\n\nevaluate_envelope(point)¶\n\nCalculate bone envelope at given point\n\nParameters:\n\npoint ([mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf]) – Point, Position in 3d space to evaluate\n\nReturns:\n\nFactor, Envelope factor\n\nReturn type:\n\nfloat in [-inf, inf]\n\nbbone_segment_index(point)¶\n\nRetrieve the index and blend factor of the B-Bone segments based on vertex position\n\nParameters:\n\npoint ([mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf]) – Point, Vertex position in armature pose space\n\nReturns:\n\n`index`, The index of the first segment joint affecting the point, int in [-inf, inf]\n\n`blend_next`, The blend factor between the given and the following joint, float in [-inf, inf]\n\nReturn type:\n\n(int in [-inf, inf], float in [-inf, inf])\n\nbbone_segment_matrix(index, *, rest=False)¶\n\nRetrieve the matrix of the joint between B-Bone segments if available\n\nParameters:\n\nindex (int in [0, inf]) – Index of the segment endpoint\n\nrest (boolean, (optional)) – Return the rest pose matrix\n\nReturns:\n\nThe resulting matrix in bone local space\n\nReturn type:\n\n[mathutils.Matrix](https://docs.blender.org/api/current/mathutils.html#mathutils.Matrix) of 4 * 4 items in [-inf, inf]\n\nThis example shows how to use B-Bone segment matrices to emulate deformation produced by the Armature modifier or constraint when assigned to the given bone (without Preserve Volume). The coordinates are processed in armature Pose space:\n\n```\ndef bbone_deform_matrix(pose_bone, point):\n index, blend_next = pose_bone.bbone_segment_index(point)\n\n rest1 = pose_bone.bbone_segment_matrix(index, rest=True)\n pose1 = pose_bone.bbone_segment_matrix(index, rest=False)\n deform1 = pose1 @ rest1.inverted()\n\n # `bbone_segment_index` ensures that index + 1 is always valid\n rest2 = pose_bone.bbone_segment_matrix(index + 1, rest=True)\n pose2 = pose_bone.bbone_segment_matrix(index + 1, rest=False)\n deform2 = pose2 @ rest2.inverted()\n\n deform = deform1 * (1 - blend_next) + deform2 * blend_next\n\n return pose_bone.matrix @ deform @ pose_bone.bone.matrix_local.inverted()\n\n\n# Armature modifier deforming vertices:\nmesh = bpy.data.objects[\"Mesh\"]\npose_bone = bpy.data.objects[\"Armature\"].pose.bones[\"Bone\"]\n\nfor vertex in mesh.data.vertices:\n vertex.co = bbone_deform_matrix(pose_bone, vertex.co) @ vertex.co\n\n# Armature constraint modifying an object transform:\nempty = bpy.data.objects[\"Empty\"]\nmatrix = empty.matrix_world\n\nempty.matrix_world = bbone_deform_matrix(pose_bone, matrix.translation) @ matrix\n\n```\n\ncompute_bbone_handles(*, rest=False, ease=False, offsets=False)¶\n\nRetrieve the vectors and rolls coming from B-Bone custom handles\n\nParameters:\n\nrest (boolean, (optional)) – Return the rest pose state\n\nease (boolean, (optional)) – Apply scale from ease values\n\noffsets (boolean, (optional)) – Apply roll and curve offsets from bone properties\n\nReturns:\n\n`handle1`, The direction vector of the start handle in bone local space, [mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf]\n\n`roll1`, Roll of the start handle, float in [-inf, inf]\n\n`handle2`, The direction vector of the end handle in bone local space, [mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf]\n\n`roll2`, Roll of the end handle, float in [-inf, inf]\n\nReturn type:\n\n([mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], float in [-inf, inf], [mathutils.Vector](https://docs.blender.org/api/current/mathutils.html#mathutils.Vector) of 3 items in [-inf, inf], float in [-inf, inf])\n\nparent_index(parent_test)¶\n\nThe same as ‘bone in other_bone.parent_recursive’ but saved generating a list.\n\ntranslate(vec)¶\n\nUtility function to add vec to the head and tail of this bone.\n\nclassmethod bl_rna_get_subclass(id, default=None, /)¶ Parameters:\n\nid (str) – The RNA type identifier.\n\nReturns:\n\nThe RNA type or default when not found.\n\nReturn type:\n\n[bpy.types.Struct](https://docs.blender.org/api/current/bpy.types.Struct.html#bpy.types.Struct) subclass\n\nclassmethod bl_rna_get_subclass_py(id, default=None, /)¶ Parameters:\n\nid (str) – The RNA type identifier.\n\nReturns:\n\nThe class or default when not found.\n\nReturn type:\n\ntype\n\n## Inherited Properties¶\n\n[bpy_struct.id_data](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.id_data)\n\n## Inherited Functions¶\n\n[bpy_struct.as_pointer](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.as_pointer)\n\n[bpy_struct.driver_add](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.driver_add)\n\n[bpy_struct.driver_remove](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.driver_remove)\n\n[bpy_struct.get](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.get)\n\n[bpy_struct.id_properties_clear](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.id_properties_clear)\n\n[bpy_struct.id_properties_ensure](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.id_properties_ensure)\n\n[bpy_struct.id_properties_ui](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.id_properties_ui)\n\n[bpy_struct.is_property_hidden](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.is_property_hidden)\n\n[bpy_struct.is_property_overridable_library](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.is_property_overridable_library)\n\n[bpy_struct.is_property_readonly](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.is_property_readonly)\n\n[bpy_struct.is_property_set](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.is_property_set)\n\n[bpy_struct.items](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.items)\n\n[bpy_struct.keyframe_delete](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.keyframe_delete)\n\n[bpy_struct.keyframe_insert](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.keyframe_insert)\n\n[bpy_struct.keys](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.keys)\n\n[bpy_struct.path_from_id](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.path_from_id)\n\n[bpy_struct.path_from_module](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.path_from_module)\n\n[bpy_struct.path_resolve](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.path_resolve)\n\n[bpy_struct.pop](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.pop)\n\n[bpy_struct.property_overridable_library_set](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.property_overridable_library_set)\n\n[bpy_struct.property_unset](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.property_unset)\n\n[bpy_struct.rna_ancestors](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.rna_ancestors)\n\n[bpy_struct.type_recast](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.type_recast)\n\n[bpy_struct.values](https://docs.blender.org/api/current/bpy.types.bpy_struct.html#bpy.types.bpy_struct.values)\n\n## References¶\n\n[bpy.context.active_pose_bone](https://docs.blender.org/api/current/bpy.context.html#bpy.context.active_pose_bone)\n\n[bpy.context.pose_bone](https://docs.blender.org/api/current/bpy.context.html#bpy.context.pose_bone)\n\n[bpy.context.selected_pose_bones](https://docs.blender.org/api/current/bpy.context.html#bpy.context.selected_pose_bones)\n\n[bpy.context.selected_pose_bones_from_active_object](https://docs.blender.org/api/current/bpy.context.html#bpy.context.selected_pose_bones_from_active_object)\n\n[bpy.context.visible_pose_bones](https://docs.blender.org/api/current/bpy.context.html#bpy.context.visible_pose_bones)\n\n[Object.convert_space](https://docs.blender.org/api/current/bpy.types.Object.html#bpy.types.Object.convert_space)\n\n[Pose.bones](https://docs.blender.org/api/current/bpy.types.Pose.html#bpy.types.Pose.bones)\n\n`PoseBone.bbone_custom_handle_end`\n\n`PoseBone.bbone_custom_handle_start`\n\n`PoseBone.child`\n\n`PoseBone.custom_shape_transform`\n\n`PoseBone.parent`"
+}
+```
+User decision: **accepted**
+
+Status: **completed**
+
+
+
+
+
+---
+
+Thought Process
+Let me read this file to see the PoseBone API.
+
+---
+
+
+Tool use: **read_file_v2** • Read file: C:\Users\Nathan\.cursor\projects\t-Dynamic-Link-Manager\agent-tools\2b59cbcc-6d6a-46a9-ac24-052eb68b5ed5.txt
+
+
+
+
+---
+
+Thought Process
+Let me search for selection-related properties in this file.
+
+---
+
+
+
+Tool use: **ripgrep_raw_search**
+
+
+Parameters:
+
+```json
+{
+ "pattern": "select",
+ "path": "C:\\Users\\Nathan\\.cursor\\projects\\t-Dynamic-Link-Manager\\agent-tools\\2b59cbcc-6d6a-46a9-ac24-052eb68b5ed5.txt",
+ "outputMode": "content",
+ "caseInsensitive": false
+}
+```
+Additional data:
+
+```json
+{
+ "isPruned": true,
+ "pattern": "select",
+ "path": "C:\\Users\\Nathan\\.cursor\\projects\\t-Dynamic-Link-Manager\\agent-tools\\2b59cbcc-6d6a-46a9-ac24-052eb68b5ed5.txt",
+ "outputMode": "content",
+ "totalFiles": 1,
+ "totalMatches": 4,
+ "topFiles": [
+ {
+ "uri": "C:\\Users\\Nathan\\.cursor\\projects\\t-Dynamic-Link-Manager\\agent-tools\\2b59cbcc-6d6a-46a9-ac24-052eb68b5ed5.txt",
+ "matchCount": 4
+ }
+ ]
+}
+```
+Status: **completed**
+
+
+
+
+
+---
+
+Thought Process
+There's a `select` property on PoseBone at line 459. Let me read around that line.
+
+---
+
+
+Tool use: **read_file_v2** • Read file: C:\Users\Nathan\.cursor\projects\t-Dynamic-Link-Manager\agent-tools\2b59cbcc-6d6a-46a9-ac24-052eb68b5ed5.txt
+
+
+
+
+---
+
+Thought Process
+The `select` property exists on PoseBone in Blender 5.0. So the correct way to select bones in Blender 5.0 is:
+```python
+rep.pose.bones[name].select = True
+```
+
+Let me update the tweak_tools.py file to use this.
+
+---
+
+Based on the Blender 5.0 API documentation, `PoseBone` has a `select` property. The correct syntax is `pose_bone.select = True`:
+
+---
+
+
+
+Tool use: **edit_file_v2** • Edit file: T:/Dynamic-Link-Manager/ops/tweak_tools.py
+
+
+
+
+
+---
+
+Thought Process
+Let me verify the fix.
+
+---
+
+
+
+Tool use: **read_lints**
+
+
+Parameters:
+
+```json
+{
+ "paths": [
+ "T:/Dynamic-Link-Manager/ops/tweak_tools.py"
+ ]
+}
+```
+Result:
+
+```json
+{
+ "linterErrorsByFile": [
+ {
+ "relativeWorkspacePath": "T:/Dynamic-Link-Manager/ops/tweak_tools.py"
+ }
+ ]
+}
+```
+Status: **completed**
+
+
+
+
+
+---
+
+Thought Process
+Fixed. The correct API for Blender 5.0 is `rep.pose.bones[name].select = True`.
+
+---
+
+Fixed. According to the Blender 5.0 API documentation, `PoseBone` has a `select` property:
+
+```python
+rep.pose.bones[name].select = True
+```
+
+This sets the bone as selected in Pose Mode. The `select` property exists directly on the `PoseBone` object (not on the `Bone` data).
+
+---
+
+_**User**_
+
+characters that aren't repchar or origchar are still not having their bone constraints remapped from orig to rep.
+
+---
+
+_**Agent (model kimi-k2.5, mode Agent)**_
+
+Thought Process
+Let me look at the current constraint retargeting logic in `run_retarg_relatives`. The user is saying that constraints on bones of characters that aren't the origchar or repchar are not being remapped.
+
+Let me read the migrator.py file to see the current implementation.
+
+---
+
+
+Tool use: **read_file_v2** • Read file: T:/Dynamic-Link-Manager/ops/migrator.py
+
+
+
+
+---
+
+Thought Process
+I see the issue. The code at lines 490-494 handles object-level constraints (where `c.target` is an object), but it doesn't handle **bone constraints** on other characters.
+
+Bone constraints are on `ob.pose.bones[...].constraints`, not on `ob.constraints`. The current code only looks at object-level constraints (`ob.constraints`).
+
+I need to add logic to iterate through all armatures and check their pose bones' constraints, retargeting any that point to `orig` to point to `rep` instead.
+
+---
+
+I see the issue. The code handles object-level constraints (`ob.constraints`), but not **bone constraints** on other armatures (`ob.pose.bones[].constraints`). Let me add bone constraint retargeting:
+
+---
+
+
+
+Tool use: **edit_file_v2** • Edit file: T:/Dynamic-Link-Manager/ops/migrator.py
+
+
+
+
+
+---
+
+Thought Process
+Good, I've added bone constraint retargeting. Now any constraint on any bone of any armature that targets the original character will be retargeted to the replacement character.
+
+---
+
+
+
+Tool use: **read_lints**
+
+
+Parameters:
+
+```json
+{
+ "paths": [
+ "T:/Dynamic-Link-Manager/ops/migrator.py"
+ ]
+}
+```
+Result:
+
+```json
+{
+ "linterErrorsByFile": [
+ {
+ "relativeWorkspacePath": "T:/Dynamic-Link-Manager/ops/migrator.py"
+ }
+ ]
+}
+```
+Status: **completed**
+
+
+
+
+
+---
+
+Thought Process
+Good, no linter errors. The fix adds a new loop that goes through all armatures in the scene and checks each pose bone's constraints, retargeting any that point to `orig` to point to `rep` instead.
+
+---
+
+Fixed. Added bone constraint retargeting for ALL armatures in the scene. The new code (lines 495-502) iterates through:
+
+1. **All armature objects** in the
+
+---
+
diff --git a/ops/migrator.py b/ops/migrator.py
index 497ac7a..b644df0 100644
--- a/ops/migrator.py
+++ b/ops/migrator.py
@@ -493,6 +493,15 @@ def run_retarg_relatives(orig, rep, rep_descendants, orig_to_rep):
if getattr(c, "target", None) == orig:
c.target = rep
+ # Retarget bone constraints on ALL armatures (other characters, etc.)
+ for ob in bpy.data.objects:
+ if ob.type != "ARMATURE" or not ob.pose:
+ continue
+ for pbone in ob.pose.bones:
+ for c in pbone.constraints:
+ if getattr(c, "target", None) == orig:
+ c.target = rep
+
# Camera DOF: retarget focus_object from orig to rep
for ob in bpy.data.objects:
if ob.type != 'CAMERA':