@Override
  protected void prepareTracksForApplyingConstraints() {
    Long[] bonesOMAs = new Long[] {ownerOMA, targetOMA};
    Space[] spaces = new Space[] {ownerSpace, targetSpace};

    // creating animations for current objects if at least on of their parents have an animation
    for (int i = 0; i < bonesOMAs.length; ++i) {
      Long oma = bonesOMAs[i];
      if (this.hasAnimation(oma)) {
        Bone currentBone = blenderContext.getBoneContext(oma).getBone();
        Bone parent = currentBone.getParent();
        boolean foundAnimation = false;
        AnimData animData = null;
        while (parent != null && !foundAnimation) {
          BoneContext boneContext = blenderContext.getBoneByName(parent.getName());
          foundAnimation = this.hasAnimation(boneContext.getBoneOma());
          animData = blenderContext.getAnimData(boneContext.getBoneOma());
          parent = parent.getParent();
        }

        if (foundAnimation) {
          this.applyAnimData(blenderContext.getBoneContext(oma), spaces[i], animData);
        }
      }
    }

    // creating animation for owner if it doesn't have one already and if the target has it
    if (!this.hasAnimation(ownerOMA) && this.hasAnimation(targetOMA)) {
      AnimData targetAnimData = blenderContext.getAnimData(targetOMA);
      this.applyAnimData(blenderContext.getBoneContext(ownerOMA), ownerSpace, targetAnimData);
    }
  }
  private void scanSpatial(Spatial model) {
    AnimControl animControl = model.getControl(AnimControl.class);
    Map<Integer, List<Float>> pointsMap = null;
    if (weightThreshold == -1.0f) {
      pointsMap = RagdollUtils.buildPointMap(model);
    }

    skeleton = animControl.getSkeleton();
    skeleton.resetAndUpdate();
    for (int i = 0; i < skeleton.getRoots().length; i++) {
      Bone childBone = skeleton.getRoots()[i];
      if (childBone.getParent() == null) {
        logger.log(Level.INFO, "Found root bone in skeleton {0}", skeleton);
        baseRigidBody =
            new PhysicsRigidBody(new BoxCollisionShape(Vector3f.UNIT_XYZ.mult(0.1f)), 1);
        baseRigidBody.setKinematic(mode == Mode.Kinematic);
        boneRecursion(model, childBone, baseRigidBody, 1, pointsMap);
      }
    }
  }
  private void boneRecursion(
      Spatial model,
      Bone bone,
      PhysicsRigidBody parent,
      int reccount,
      Map<Integer, List<Float>> pointsMap) {
    PhysicsRigidBody parentShape = parent;
    if (boneList.isEmpty() || boneList.contains(bone.getName())) {

      PhysicsBoneLink link = new PhysicsBoneLink();
      link.bone = bone;

      // creating the collision shape
      HullCollisionShape shape = null;
      if (pointsMap != null) {
        // build a shape for the bone, using the vertices that are most influenced by this bone
        shape =
            RagdollUtils.makeShapeFromPointMap(
                pointsMap,
                RagdollUtils.getBoneIndices(link.bone, skeleton, boneList),
                initScale,
                link.bone.getModelSpacePosition());
      } else {
        // build a shape for the bone, using the vertices associated with this bone with a weight
        // above the threshold
        shape =
            RagdollUtils.makeShapeFromVerticeWeights(
                model,
                RagdollUtils.getBoneIndices(link.bone, skeleton, boneList),
                initScale,
                link.bone.getModelSpacePosition(),
                weightThreshold);
      }

      PhysicsRigidBody shapeNode = new PhysicsRigidBody(shape, rootMass / (float) reccount);

      shapeNode.setKinematic(mode == Mode.Kinematic);
      totalMass += rootMass / (float) reccount;

      link.rigidBody = shapeNode;
      link.initalWorldRotation = bone.getModelSpaceRotation().clone();

      if (parent != null) {
        // get joint position for parent
        Vector3f posToParent = new Vector3f();
        if (bone.getParent() != null) {
          bone.getModelSpacePosition()
              .subtract(bone.getParent().getModelSpacePosition(), posToParent)
              .multLocal(initScale);
        }

        SixDofJoint joint =
            new SixDofJoint(parent, shapeNode, posToParent, new Vector3f(0, 0, 0f), true);
        preset.setupJointForBone(bone.getName(), joint);

        link.joint = joint;
        joint.setCollisionBetweenLinkedBodys(false);
      }
      boneLinks.put(bone.getName(), link);
      shapeNode.setUserObject(link);
      parentShape = shapeNode;
    }

    for (Iterator<Bone> it = bone.getChildren().iterator(); it.hasNext(); ) {
      Bone childBone = it.next();
      boneRecursion(model, childBone, parentShape, reccount + 1, pointsMap);
    }
  }