Example #1
0
    def getBaseRotation(self):
        """
        DON'T USE (it's not necessary)

        Returns the base rotation matrix of the bone associated with this joint.
        The base rotation matrix rotates the vector [0 length 0] to the offset
        vector. "length" is computed through self.getLength and "offset" through
        self.offset.

        Motion Capture File Formats Explained. M. Meredith S.Maddock
        """
        if len(self.baserotation) == 0:
            self.getLength()
            try:
                euler, warning = mathutils.eulerFromMatrix(
                    mathutils.alignVectors(
                        self.getChildren(0).offset, [0, 1.0, 0]), self.order)
            except:
                print('Endsite used in getBaseRotation(joint)')
                euler, warning = mathutils.eulerFromMatrix(
                    mathutils.alignVectors(self.endsite, [0, 1.0, 0]),
                    self.order)
            if warning:
                print('Instability found in getBaseRotation(%s)' % self.name)
            self.baserotation = euler
        return self.baserotation
Example #2
0
    def getRecalcRotationMatrix(self, frame):
        """
        ESSA FUNçÂO NÂO DEVE SER UTILIZADA
        Returns the recalculated local rotation matrix

        Equation 4.9 from Motion Capture File Formats Explained. M. Meredith S.Maddock
        """
        #TODO: Eu preciso de um jeito de calcular a rotação global com a rotação base
        # pq minha rotação global atual não leva em conta a base, então pode estar
        # apontando para o lugar errado
        #TODO: Função obsoleta, testei e não deu certo, fui por outro caminho.
        #ESSA FUNçÂO NÂO DEVE SER UTILIZADA

        #Get the hierarchy from joint to root
        tree_parentjointTOroot = list([joint for joint in reversed(self)])
        stack = mathutils.matrixIdentity()

        for joint in tree_parentjointTOroot:
            #Creates base matrix
            try:
                basematrix = mathutils.alignVectors(
                    joint.getChildren(0).offset, [0, 1.0, 0]).T
            except:
                print('Endsite used in getBaseRotation(joint)')
                basematrix = mathutils.alignVectors(joint.endsite,
                                                    [0, 1.0, 0]).T
            stack = np.dot(stack, basematrix)

        matrix = np.dot(
            stack, mathutils.matrixR(self.getLocalRotation(frame), self.order))
        stack = stack.T
        try:
            basematrix = mathutils.alignVectors(
                self.getChildren(0).offset, [0, 1.0, 0])
        except:
            print('Endsite used in getBaseRotation(joint)')
            basematrix = mathutils.alignVectors(self.endsite, [0, 1.0, 0])
        stack = np.dot(stack, basematrix)
        matrix = np.dot(matrix, stack)
        return matrix
Example #3
0
def PostureInitialization(ani_ava, ani_mocap, getpositions=False, headAlign = True, spineAlign = True, handAlign = True):
    """
    Copy the rotation from the mocap joints to the corresponding avatar joint.

    ani_ava: Avatar animation
    ani_mocap: Mocap animation
    """
    #Get mapping
    mocapmap = ani_mocap.getskeletonmap()
    avamap = ani_ava.getskeletonmap()
    #
    #Save the reference TPose
    for joint in ani_ava.getlistofjoints():
        joint.tposerot = joint.rotation[0]
        joint.tposetrans = joint.translation[0]

    start=time.time()
    #Expand the number of frames of the avatar animation to match the mocap animation
    ani_ava.expandFrames(mocapmap.root.translation.shape[0])
    #Adapt pose each frame
    print('Starting Posture Initialization')
    for frame in range(ani_mocap.frames):
        if np.mod(frame+1,100) == 0:
            print('%i frames done. %s seconds.' % (int((frame+1)/100)*100,time.time()-start))
            start=time.time()

        #Get the Height of the root in the base position (Frame = 0)
        #If the source animation (mocap) is not in the TPose, it will fail
        if frame == 0:
            ground_normal = np.array([0,1,0])
            srcHHips = np.dot(mocapmap.hips.getPosition(0), ground_normal)
            tgtHHips = np.dot(avamap.hips.getPosition(0), ground_normal)
            ratio = tgtHHips/srcHHips

        #Adjust roots/hips height
        #Eray Molla Eq 1
        srcPosHips = mocapmap.hips.getPosition(frame)
        srcGroundHips = np.asarray([srcPosHips[0], 0, srcPosHips[2]])
        tgtGroundHips = srcGroundHips*ratio
        srcHHips = np.dot(mocapmap.hips.getPosition(frame), ground_normal)
        tgtHHips = srcHHips*ratio
        avamap.root.translation[frame] = [0,tgtHHips,0] + tgtGroundHips

        if frame == 0:
            mocapbones = []
            avabones = []
            if spineAlign:
                mocapbones.append([mocapmap.hips, mocapmap.spine3])
                avabones.append([avamap.hips, avamap.spine3])
            if headAlign:
                mocapbones.append([mocapmap.neck, mocapmap.head])
                avabones.append([avamap.neck, avamap.head])                
            mocapbones = mocapbones + [[mocapmap.rarm, mocapmap.rforearm],[mocapmap.larm, mocapmap.lforearm],[mocapmap.rforearm, mocapmap.rhand],[mocapmap.lforearm, mocapmap.lhand],[mocapmap.rupleg, mocapmap.rlowleg],[mocapmap.lupleg, mocapmap.llowleg],[mocapmap.rlowleg, mocapmap.rfoot],[mocapmap.llowleg, mocapmap.lfoot]]
            avabones = avabones + [[avamap.rarm, avamap.rforearm],[avamap.larm, avamap.lforearm],[avamap.rforearm, avamap.rhand],[avamap.lforearm, avamap.lhand],[avamap.rupleg, avamap.rlowleg],[avamap.lupleg, avamap.llowleg],[avamap.rlowleg, avamap.rfoot],[avamap.llowleg, avamap.lfoot]]
            if handAlign and mocapmap.lhandmiddle and mocapmap.rhandmiddle and avamap.lhandmiddle and avamap.rhandmiddle:
                mocapbones = mocapbones + [[mocapmap.rhand, mocapmap.rhandmiddle],[mocapmap.lhand, mocapmap.lhandmiddle]]
                avabones = avabones + [[avamap.rhand, avamap.rhandmiddle],[avamap.lhand, avamap.lhandmiddle]]
            for mocapbone, avabone in zip(mocapbones,avabones):
                #Get source and target global transform and rotation matrices from the start of the bone
                p0 = mocapbone[0].getPosition(0)
                p1 = mocapbone[1].getPosition(0)
                srcDirection = mathutils.unitVector(p1-p0)
                #Get source and target global transform and rotation matrices from the end of the bone
                p0 = avabone[0].getPosition(0)
                p1 = avabone[1].getPosition(0)
                tgtDirection = mathutils.unitVector(p1-p0)
                #Align vectors
                alignMat = mathutils.alignVectors(tgtDirection, srcDirection)
                #Get new global rotation matrix
                tgtGlbTransformMat = avabone[0].getGlobalTransform(frame)
                tgtGlbRotationMat = mathutils.shape4ToShape3(tgtGlbTransformMat)
                tgtNewGblRotationMat = np.dot(alignMat,tgtGlbRotationMat)
                #Get new local rotation matrix
                if not avabone[0] == avamap.root: #Does not have a parent, transform is already local
                    tgtParentGblRotationMat = mathutils.shape4ToShape3(avabone[0].parent.getGlobalTransform(frame))
                    tgtNewLclRotationMat = np.dot(tgtParentGblRotationMat.T, tgtNewGblRotationMat)
                else:
                    tgtNewLclRotationMat = tgtNewGblRotationMat[:]
                #Get new local rotation euler angles
                tgtNewLclRotationEuler, warning = mathutils.eulerFromMatrix(tgtNewLclRotationMat, avabone[0].order)
                avabone[0].rotation[frame] = tgtNewLclRotationEuler
                
        else:
            for joint_ava, joint_mocap in zip(avamap.getJointsNoRootHips(), mocapmap.getJointsNoRootHips()):
                if joint_ava is not None and joint_mocap is not None:
                    previousframe = frame-1 if frame!= 0 else 0
                    #Get source and target global transform and rotation matrices
                    #Even if frame == 0 the matrices need to be recalculated
                    srcGlbTransformMat = joint_mocap.getGlobalTransform(frame)
                    srcGlbRotationMat = mathutils.shape4ToShape3(srcGlbTransformMat)
                    tgtGlbTransformMat = joint_ava.getGlobalTransform(previousframe)
                    tgtGlbRotationMat = mathutils.shape4ToShape3(tgtGlbTransformMat)
                    #Get previous source global transform and rotation matrices
                    srcPreviousGlbTransformMat = joint_mocap.getGlobalTransform(previousframe)
                    srcPreviousGlbRotationMat = mathutils.shape4ToShape3(srcPreviousGlbTransformMat)
                    #Get the transform of the source from the previous frame to the present frame
                    transform = np.dot(srcGlbRotationMat, srcPreviousGlbRotationMat.T)
                    #Apply transform
                    tgtNewGblRotationMat = np.dot(transform, tgtGlbRotationMat)
                    #Get new local rotation matrix
                    tgtParentGblRotationMat = mathutils.shape4ToShape3(joint_ava.parent.getGlobalTransform(frame))
                    tgtNewLclRotationMat = np.dot(tgtParentGblRotationMat.T, tgtNewGblRotationMat)
                    #Get new local rotation euler angles
                    tgtNewLclRotationEuler, warning = mathutils.eulerFromMatrix(tgtNewLclRotationMat, joint_ava.order)
                    joint_ava.rotation[frame] = tgtNewLclRotationEuler[:]

        ani_ava.frames = ani_mocap.frames
        ani_ava.frametime = ani_mocap.frametime