PDA

View Full Version : Using bone.lookat for bones other than head


omidbrb
02-27-2009, 03:01 AM
Hi!

Is it possible to use bone.lookat for bones other than the head? I use the following code to always point the hand towards an object but it stays perpendicular!


def lookAtBall():
bone = avatar.getBone('Bip01 L Forearm')
bone.lock();
bone.lookat(ball.getPosition(),0,viz.ABS_GLOBAL)

vizact.ontimer(.5,lookAtBall)


Could you give me some hints why it's not working?

Best,
Omid

Jeff
03-03-2009, 10:02 AM
Here is the forearm added to an example that Farshizzo recently posted for using lookat. It works for other bones, I just had to subtract 90 degrees from the yaw value to make it look right.

import viz
import vizact
viz.go()

viz.add('tut_ground.wrl')

#Create animating ball
ball = viz.add('white_ball.wrl')
ball.add(vizact.sequence(vizact.goto(-2,1,0),vizact.goto(2,1,0),viz.FOREVER))

#Create male avatar
avatar1 = viz.add('vcc_male.cfg',pos=(-2,0,3),euler=(180,0,0))
avatar1.state(1)
head1 = avatar1.getBone('Bip01 Head')
head1.lock()

#Create female avatar
avatar2 = viz.add('vcc_female.cfg',pos=(2,0,3),euler=(180,0, 0))
avatar2.state(1)
head2 = avatar2.getBone('Bip01 Head')
forearm = avatar2.getBone('Bip01 R Forearm')

head2.lock()

def UpdateAvatarHead():
"""Update avatars to look at ball position"""
pos = ball.getPosition()

head1.lookat(pos,0,viz.AVATAR_WORLD)
head2.lookat(pos,0,viz.AVATAR_WORLD)

forearm.lookat(pos,0,viz.AVATAR_WORLD)
ori = forearm.getEuler(viz.AVATAR_WORLD)
forearm.setEuler([ori[0] - 90, ori[1], ori[2]], viz.AVATAR_WORLD)


vizact.ontimer(0,UpdateAvatarHead)

viz.MainView.move(0,0,-5)

omidbrb
03-24-2009, 03:54 AM
Hi,

Thanks for the example code. I added 60 degrees to the roll and now it looks better. I did the same experiment with left upper arm, and I had to make a different correction to make it right.

My impression is that the lookat function makes the joint to look at a certain direction and the bone connected to the joint is not in 0 degrees relative to the joint. Am I right? Is it a way to find the exact corrections for each bone?


The code below is the modified code:


import viz
import vizact
viz.go()

viz.add('tut_ground.wrl')

#Create animating ball
ball = viz.add('white_ball.wrl')
ball.add(vizact.sequence(vizact.goto(1,1.3,2.5),vi zact.goto(3,1.3,2.5),viz.FOREVER))

#Create male avatar
avatar1 = viz.add('vcc_male.cfg',pos=(-2,0,3),euler=(180,0,0))
avatar1.state(1)
head1 = avatar1.getBone('Bip01 Head')
head1.lock()

#Create female avatar
avatar2 = viz.add('vcc_female.cfg',pos=(2,0,3),euler=(180,0, 0))
avatar2.state(1)
head2 = avatar2.getBone('Bip01 Head')
forearm = avatar2.getBone('Bip01 R Forearm')
arm = avatar2.getBone('Bip01 L UpperArm')

head2.lock()

def UpdateAvatarHead():
"""Update avatars to look at ball position"""
pos = ball.getPosition()

head1.lookat(pos,0,viz.AVATAR_WORLD)
head2.lookat(pos,0,viz.AVATAR_WORLD)

forearm.lookat(pos,0,viz.AVATAR_WORLD)
ori = forearm.getEuler(viz.AVATAR_WORLD)
forearm.setEuler([ori[0] - 90, ori[1], ori[2]+60], viz.AVATAR_WORLD)

arm.lookat(pos,0,viz.AVATAR_WORLD)
ori = arm.getEuler(viz.AVATAR_WORLD)
arm.setEuler([ori[0]+120, ori[1]+60, ori[2]+30], viz.AVATAR_WORLD)


vizact.ontimer(0,UpdateAvatarHead)

viz.MainView.move(2,0,-5)

Jeff
03-30-2009, 12:48 PM
It seems like the lookAt method takes the origin of the bone and has that look at the position you pass to it . If you want the end of the bone to look at something you may have to add some rotation to make it look right. Farshizzo, please correct me if I'm wrong about this.

omidbrb
03-31-2009, 02:46 AM
That's right, but since I need to control the bones precisely, I want to have the precise rotations that make the end of the bone point at a certain direction. Do you think it's possible?

Jeff
04-02-2009, 02:15 PM
I not quite sure how to calculate the exact offsets for all the angles. Farshizzo's on vacation for a little while but I'm sure he'll have some idea when he gets back. Do you only need to do this for the arm bones?

Gladsomebeast
04-05-2009, 12:57 PM
Interesting... What will you do with this, omidbrb?

Seems you could get the local bounding box of a bone, find the box face center point that is furthest from the bone origin, compute the angle between the bone's x-axis and the center point of the furthest box face, and rotate that angle difference after the lookat command.

omidbrb
04-23-2009, 05:21 AM
Seems you could get the local bounding box of a bone, find the box face center point that is furthest from the bone origin, compute the angle between the bone's x-axis and the center point of the furthest box face, and rotate that angle difference after the lookat command.

It seems a bit complicated to me but it'll probably work. I'm actually need it to implement Inverse Kinematics for the avatar hand movements. At the moment I'm gathering data using an exhaustive search through a set of discrete possibilities.