WorldViz User Forum

WorldViz User Forum (https://forum.worldviz.com/index.php)
-   Vizard (https://forum.worldviz.com/forumdisplay.php?f=17)
-   -   Making a HD Complete Character blink (https://forum.worldviz.com/showthread.php?t=4839)

Frank Verberne 10-02-2013 08:20 AM

Making a HD Complete Character blink
 
Hi all,

I'm trying to get a HD Complete Character to blink. HD Complete Characters have bones for facial expressions, so I thought that I had to control the bones of the eye lids to make them blink. However, I have difficulties getting a HD Complete Character to blink with using the eye lid bones. See the code below for my code. I thought rotating either the EyeBlinkTop or EyeBlinkBottom bones should do the trick, however it does not. Any help would be greatly appreciated!

Code:

import viz

viz.go()

avatar = viz.add('vcc_male2.cfg', pos = [0,.15,.5], euler = [180,0,0])

blinkLeft = avatar.getBone('Bip01 LEyeBlinkTop')
blinkRight = avatar.getBone('Bip01 REyeBlinkBottom')
blinkLeft.lock()
blinkRight.lock()

def onKeyDown(key):
        eulerLeft = blinkLeft.getEuler(viz.AVATAR_LOCAL)
        eulerRight = blinkRight.getEuler(viz.AVATAR_LOCAL)
        if key in 'qQ':
                eulerLeft[0] += 1
                eulerRight[0] += 1
        elif key in 'aA':
                eulerLeft[0] -= 1
                eulerRight[0] -= 1
        elif key in 'wW':
                eulerLeft[1] += 1
                eulerRight[1] += 1
        elif key in 'eE':
                eulerLeft[1] -= 1
                eulerRight[1] -= 1
        elif key in 'sS':
                eulerLeft[2] += 1
                eulerRight[2] += 1
        elif key in 'dD':
                eulerLeft[2] -= 1
                eulerRight[2] -= 1
        blinkLeft.setEuler(eulerLeft, viz.AVATAR_LOCAL)
        blinkRight.setEuler(eulerRight, viz.AVATAR_LOCAL)

viz.callback(viz.KEYDOWN_EVENT,onKeyDown)


Jeff 10-03-2013 05:39 PM

Most of the animations included with the HD characters have blinking included. You could print out the bone values with an animation running to see how the values change over time. To create a blinking effect as natural as the animations the bone rotations would probably require a non linear function.

Frank Verberne 10-15-2013 08:20 AM

Hi Jeff,

Sounds like a good idea! However, I've tried to print the eulers (also tried quaternions) of the eye related bones, while running one of the standard animations and was unable to detect changes in eulers (or quaternions) of those bones. So I don't know how the HD character blinks during the standard animations. In its cfg file, no blink morph is specified, so blinking is not accomplished through applying a moprh. Any suggestions?

Code:

import viz
import vizact

viz.go()

avatar = viz.add('vcc_male2.cfg', pos = [0,.15,.25], euler = [180,0,0])
avatar.state(1)
boneList = []

for bone in avatar.getBoneList():
        if 'Eye' in bone.getName() and not (('brow' in bone.getName()) or 'Nub' in bone.getName()):
                boneList.append(bone)

def printInfo():
        for bone in boneList:
                print bone.getName(), bone.getEuler()
       
vizact.ontimer(viz.FASTEST_EXPIRATION, printInfo)


Frank Verberne 10-16-2013 01:26 AM

Okay, I'm pretty sure the eyelids are not moved by bones. I've tried recording a little piece of one of the standard animations of the sample HD character, with blinking included. Uncomment vizact.onexit(saveTrackingData) to enable saving. Warning: the resulting file gets big (for a .log file) fast:
Code:

import viz
import vizact
import cPickle

viz.go()

avatar = viz.add('vcc_male2.cfg', pos = [0,.15,.25], euler = [180,0,0])
avatar.state(1)
boneList = []
boneNameList = []

for bone in avatar.getBoneList():
        boneList.append(bone)
        boneNameList.append(bone.getName())

global bone_info, total_info
bone_info = []
total_info = []

def updateBoneInfo():
        global bone_info, total_info
        for bone in boneList:
                bone_info.append(bone.getName())
                bone_info.append(bone.getEuler())
        total_info.append(bone_info)
        bone_info = []

vizact.ontimer(viz.FASTEST_EXPIRATION, updateBoneInfo)

BONE_DATA = open("Recording_of_bones.log", 'w+')

def saveTrackingData():
        global total_info
        cPickle.dump(total_info, BONE_DATA)
        BONE_DATA.flush()
        BONE_DATA.close()

#vizact.onexit(saveTrackingData)

Then, I played back the recordings on the same avatar, and the whole animation is played back, EXCEPT for the blinking (press the b-key for playback if the previous code is used to create a short recording):
Code:

import viz
import vizact
import viztask
import cPickle
from collections import deque

viz.go()

avatar = viz.add('vcc_male2.cfg', pos = [0,.15,.25], euler = [180,0,0])
boneList = []
boneNameList = []

for bone in avatar.getBoneList():
        boneList.append(bone)
        boneNameList.append(bone.getName())

for bone in boneList:
        bone.lock()
       
BONE_DATA = open("Recording_of_bones.log", 'r')

def setBones():
        total_info = deque(cPickle.load(BONE_DATA))
        yield viztask.waitDraw()
        while len(total_info) > 0:
                line = line = deque(total_info.popleft())
                while len(line) > 0:
                        boneName = line.popleft()
                        boneOrientation = line.popleft()
                        if boneName in boneNameList:
                                index = boneNameList.index(boneName)
                                boneList[index].setEuler(boneOrientation)
                        else:
                                print 'bone not found on character!'
                yield viztask.waitDraw()

def onKeyDown(key):
        if key in 'bB':
                viztask.schedule(setBones)

viz.callback(viz.KEYDOWN_EVENT,onKeyDown)

So that would rule out any bone involvement in blinking of the eyes. Any other suggestions?

Kevin Chiu 10-18-2013 12:07 AM

1 Attachment(s)
Hi Frank,

Please try the quick example which shown the idea for how to animating a blinking eye.
Actually it will need to move the bones positions more rather then just the orientations.
But the batter way for doing this will be animate the bones with matrix which include both the positions and rotations.

Hope this helps.

Kevin Chiu 10-18-2013 05:37 PM

1 Attachment(s)
Hi Frank,

For your information, the blink animation at my example which I post previously was played back at a slowdown speed for showing the idea.
Here is another example which will playback the blink animation at normal speed.

Cheers,

Frank Verberne 10-21-2013 12:36 PM

Hi Kevin,

Thank you very much for your example! I managed to get the animation I wanted. Never thought about the position of the bones (and never worked with matrices in Vizard), but it worked like a charm!

Cheers,
Frank

Frank Verberne 10-22-2013 08:11 AM

Just updated the code. Old version:
Code:

def playback():
        def subTask():
                for bones in boneObjList:
                        bones.lock()
                currentBone = 0
               
                for mat in boneMatList:
                        boneObjList[currentBone].setMatrix(mat, viz.ABS_PARENT)
                        yield None
                        if currentBone+1 == len(boneObjList):
                                currentBone = 0
                        else:
                                currentBone += 1
                               
                for bones in boneObjList:
                        bones.unlock()
               
        viztask.schedule( subTask() )

# Press the space key for playing back the blink animation
vizact.onkeydown(' ', playback)

A little more pyhtonic:
Code:

def playback():
        def subTask():
                for bones in boneObjList:
                        bones.lock()
               
                for i, mat in enumerate(boneMatList):
                        boneObjList[i % len(boneObjList)].setMatrix(mat, viz.ABS_PARENT)
                        yield viztask.waitDraw()
                               
                for bones in boneObjList:
                        bones.unlock()
               
        viztask.schedule( subTask() )

# Press the space key for playing back the blink animation
vizact.onkeydown(' ', playback)



All times are GMT -7. The time now is 04:21 AM.

Powered by vBulletin® Version 3.8.7
Copyright ©2000 - 2024, vBulletin Solutions, Inc.
Copyright 2002-2023 WorldViz LLC