53 pxr::UsdSkelSkeleton &skel,
54 pxr::UsdSkelAnimation &skel_anim,
60 pxr::VtTokenArray joints;
61 pxr::VtArray<float> bone_lengths;
62 pxr::VtArray<pxr::GfMatrix4d> bind_xforms;
63 pxr::VtArray<pxr::GfMatrix4d> rest_xforms;
66 auto visitor = [&](
const Bone *bone) {
71 if (deform_bones && !deform_bones->
contains(bone->name)) {
78 bone_lengths.push_back(bone->length);
81 const pxr::GfMatrix4f arm_mat(bone->arm_mat);
82 bind_xforms.push_back(pxr::GfMatrix4d(arm_mat));
89 else if (bone->parent) {
90 pxr::GfMatrix4f parent_arm_mat(bone->parent->arm_mat);
91 const pxr::GfMatrix4f rest_mat = arm_mat * parent_arm_mat.GetInverse();
92 rest_xforms.push_back(pxr::GfMatrix4d(rest_mat));
95 rest_xforms.push_back(pxr::GfMatrix4d(arm_mat));
100 skel.GetJointsAttr().Set(joints);
101 skel.GetBindTransformsAttr().Set(bind_xforms);
102 skel.GetRestTransformsAttr().Set(rest_xforms);
104 const pxr::UsdPrim skel_prim = skel.GetPrim();
107 const pxr::UsdGeomPrimvarsAPI pv_api = pxr::UsdGeomPrimvarsAPI(skel_prim);
108 pxr::UsdGeomPrimvar pv_lengths = pv_api.CreatePrimvar(
110 pv_lengths.Set(bone_lengths);
112 pxr::UsdSkelBindingAPI usd_skel_api = pxr::UsdSkelBindingAPI::Apply(skel_prim);
115 usd_skel_api.CreateAnimationSourceRel().SetTargets(
116 pxr::SdfPathVector({pxr::SdfPath(skel_anim.GetPath().GetName())}));
126 const pxr::UsdTimeCode time,
128 pxr::UsdUtilsSparseValueWriter &value_writer)
130 if (!(skel_anim &&
obj &&
obj->pose)) {
134 pxr::VtArray<pxr::GfMatrix4d> xforms;
142 if (deform_map && !deform_map->
contains(pchan->bone->name)) {
152 pxr::VtArray<pxr::GfVec3f> translations;
153 pxr::VtArray<pxr::GfQuatf> rotations;
154 pxr::VtArray<pxr::GfVec3h> scales;
155 if (pxr::UsdSkelDecomposeTransforms(xforms, &translations, &rotations, &scales)) {
156 set_attribute(skel_anim.GetTranslationsAttr(), translations, time, value_writer);
157 set_attribute(skel_anim.GetRotationsAttr(), rotations, time, value_writer);
158 set_attribute(skel_anim.GetScalesAttr(), scales, time, value_writer);
161 CLOG_WARN(&
LOG,
"Could not decompose skeleton transforms for frame time %f", time.GetValue());
169 if (!(context.object && context.object->type ==
OB_ARMATURE && context.object->data)) {
176 pxr::UsdSkelSkeleton skel = pxr::UsdSkelSkeleton::Define(stage,
usd_export_context_.usd_path);
180 "Couldn't define UsdSkelSkeleton %s",
185 pxr::UsdSkelAnimation skel_anim;
197 skel_anim = pxr::UsdSkelAnimation::Define(stage, anim_path);
200 CLOG_WARN(&
LOG,
"Couldn't define UsdSkelAnimation %s", anim_path.GetString().c_str());
211 initialize(context.object, skel, skel_anim, deform_map, allow_unicode);
static void add_anim_sample(pxr::UsdSkelAnimation &skel_anim, const Object *obj, const pxr::UsdTimeCode time, const blender::Map< blender::StringRef, const Bone * > *deform_map, pxr::UsdUtilsSparseValueWriter &value_writer)