Merge pull request #1119 from ey6es/master

Gaze adjustments: use the eye positions from the face model, subtract long term average relative to window (not head).
This commit is contained in:
Philip Rosedale 2013-10-24 18:08:06 -07:00
commit 256ca85efe
3 changed files with 31 additions and 26 deletions

View file

@ -371,12 +371,12 @@ void Application::paintGL() {
_myCamera.setUpShift (0.0f); _myCamera.setUpShift (0.0f);
_myCamera.setDistance (0.0f); _myCamera.setDistance (0.0f);
_myCamera.setTightness (0.0f); // Camera is directly connected to head without smoothing _myCamera.setTightness (0.0f); // Camera is directly connected to head without smoothing
_myCamera.setTargetPosition(_myAvatar.getHeadJointPosition()); _myCamera.setTargetPosition(_myAvatar.getHead().calculateAverageEyePosition());
_myCamera.setTargetRotation(_myAvatar.getHead().getOrientation()); _myCamera.setTargetRotation(_myAvatar.getHead().getOrientation());
} else if (_myCamera.getMode() == CAMERA_MODE_FIRST_PERSON) { } else if (_myCamera.getMode() == CAMERA_MODE_FIRST_PERSON) {
_myCamera.setTightness(0.0f); // In first person, camera follows head exactly without delay _myCamera.setTightness(0.0f); // In first person, camera follows head exactly without delay
_myCamera.setTargetPosition(_myAvatar.getEyeLevelPosition()); _myCamera.setTargetPosition(_myAvatar.getHead().calculateAverageEyePosition());
_myCamera.setTargetRotation(_myAvatar.getHead().getCameraOrientation()); _myCamera.setTargetRotation(_myAvatar.getHead().getCameraOrientation());
} else if (_myCamera.getMode() == CAMERA_MODE_THIRD_PERSON) { } else if (_myCamera.getMode() == CAMERA_MODE_THIRD_PERSON) {
@ -386,15 +386,7 @@ void Application::paintGL() {
} else if (_myCamera.getMode() == CAMERA_MODE_MIRROR) { } else if (_myCamera.getMode() == CAMERA_MODE_MIRROR) {
_myCamera.setTightness(0.0f); _myCamera.setTightness(0.0f);
_myCamera.setDistance(0.3f); _myCamera.setDistance(0.3f);
glm::vec3 targetPosition = _myAvatar.getUprightHeadPosition(); _myCamera.setTargetPosition(_myAvatar.getHead().calculateAverageEyePosition());
if (_myAvatar.getHead().getFaceModel().isActive()) {
// make sure we're aligned to the blend face eyes
glm::vec3 leftEyePosition, rightEyePosition;
if (_myAvatar.getHead().getFaceModel().getEyePositions(leftEyePosition, rightEyePosition)) {
targetPosition = (leftEyePosition + rightEyePosition) * 0.5f;
}
}
_myCamera.setTargetPosition(targetPosition);
_myCamera.setTargetRotation(_myAvatar.getWorldAlignedOrientation() * glm::quat(glm::vec3(0.0f, PIf, 0.0f))); _myCamera.setTargetRotation(_myAvatar.getWorldAlignedOrientation() * glm::quat(glm::vec3(0.0f, PIf, 0.0f)));
} }
@ -1765,7 +1757,7 @@ Avatar* Application::findLookatTargetAvatar(const glm::vec3& mouseRayOrigin, con
float distance; float distance;
if (rayIntersectsSphere(mouseRayOrigin, mouseRayDirection, headPosition, if (rayIntersectsSphere(mouseRayOrigin, mouseRayDirection, headPosition,
HEAD_SPHERE_RADIUS * avatar->getHead().getScale(), distance)) { HEAD_SPHERE_RADIUS * avatar->getHead().getScale(), distance)) {
eyePosition = avatar->getHead().getEyePosition(); eyePosition = avatar->getHead().calculateAverageEyePosition();
_lookatIndicatorScale = avatar->getHead().getScale(); _lookatIndicatorScale = avatar->getHead().getScale();
_lookatOtherPosition = headPosition; _lookatOtherPosition = headPosition;
nodeUUID = avatar->getOwningNode()->getUUID(); nodeUUID = avatar->getOwningNode()->getUUID();
@ -1932,10 +1924,15 @@ void Application::update(float deltaTime) {
if (_lookatTargetAvatar && !_faceshift.isActive()) { if (_lookatTargetAvatar && !_faceshift.isActive()) {
// If the mouse is over another avatar's head... // If the mouse is over another avatar's head...
_myAvatar.getHead().setLookAtPosition(lookAtSpot); _myAvatar.getHead().setLookAtPosition(lookAtSpot);
} else if (_isHoverVoxel && !_faceshift.isActive()) { } else if (_isHoverVoxel && !_faceshift.isActive()) {
// Look at the hovered voxel // Look at the hovered voxel
lookAtSpot = getMouseVoxelWorldCoordinates(_hoverVoxel); lookAtSpot = getMouseVoxelWorldCoordinates(_hoverVoxel);
_myAvatar.getHead().setLookAtPosition(lookAtSpot); _myAvatar.getHead().setLookAtPosition(lookAtSpot);
} else if (_myCamera.getMode() == CAMERA_MODE_MIRROR && !_faceshift.isActive()) {
_myAvatar.getHead().setLookAtPosition(_myCamera.getPosition());
} else { } else {
// Just look in direction of the mouse ray // Just look in direction of the mouse ray
const float FAR_AWAY_STARE = TREE_SCALE; const float FAR_AWAY_STARE = TREE_SCALE;
@ -2792,9 +2789,6 @@ void Application::displaySide(Camera& whichCamera, bool selfAvatarOnly) {
} }
// Render my own Avatar // Render my own Avatar
if (whichCamera.getMode() == CAMERA_MODE_MIRROR && !_faceshift.isActive()) {
_myAvatar.getHead().setLookAtPosition(whichCamera.getPosition());
}
_myAvatar.render(whichCamera.getMode() == CAMERA_MODE_MIRROR, _myAvatar.render(whichCamera.getMode() == CAMERA_MODE_MIRROR,
Menu::getInstance()->isOptionChecked(MenuOption::AvatarAsBalls)); Menu::getInstance()->isOptionChecked(MenuOption::AvatarAsBalls));
_myAvatar.setDisplayingLookatVectors(Menu::getInstance()->isOptionChecked(MenuOption::LookAtVectors)); _myAvatar.setDisplayingLookatVectors(Menu::getInstance()->isOptionChecked(MenuOption::LookAtVectors));

View file

@ -238,6 +238,11 @@ void Head::simulate(float deltaTime, bool isMine) {
} }
_faceModel.simulate(deltaTime); _faceModel.simulate(deltaTime);
calculateGeometry();
// the blend face may have custom eye meshes
_faceModel.getEyePositions(_leftEyePosition, _rightEyePosition);
} }
void Head::calculateGeometry() { void Head::calculateGeometry() {
@ -286,8 +291,6 @@ void Head::render(float alpha, bool isMine) {
_renderAlpha = alpha; _renderAlpha = alpha;
if (!(_videoFace.render(alpha) || _faceModel.render(alpha))) { if (!(_videoFace.render(alpha) || _faceModel.render(alpha))) {
calculateGeometry();
glEnable(GL_DEPTH_TEST); glEnable(GL_DEPTH_TEST);
glEnable(GL_RESCALE_NORMAL); glEnable(GL_RESCALE_NORMAL);
@ -299,11 +302,6 @@ void Head::render(float alpha, bool isMine) {
renderNose(); renderNose();
renderEyeBrows(); renderEyeBrows();
} }
if (_faceModel.isActive()) {
// the blend face may have custom eye meshes
_faceModel.getEyePositions(_leftEyePosition, _rightEyePosition);
}
if (_renderLookatVectors) { if (_renderLookatVectors) {
renderLookatVectors(_leftEyePosition, _rightEyePosition, _lookAtPosition); renderLookatVectors(_leftEyePosition, _rightEyePosition, _lookAtPosition);

View file

@ -12,6 +12,7 @@
#include "Faceshift.h" #include "Faceshift.h"
#include "Menu.h" #include "Menu.h"
#include "Util.h"
using namespace fs; using namespace fs;
using namespace std; using namespace std;
@ -63,11 +64,23 @@ void Faceshift::update() {
} }
float averageEyePitch = (_eyeGazeLeftPitch + _eyeGazeRightPitch) / 2.0f; float averageEyePitch = (_eyeGazeLeftPitch + _eyeGazeRightPitch) / 2.0f;
float averageEyeYaw = (_eyeGazeLeftYaw + _eyeGazeRightYaw) / 2.0f; float averageEyeYaw = (_eyeGazeLeftYaw + _eyeGazeRightYaw) / 2.0f;
// get the gaze relative to the window
glm::vec3 eyeEulers = safeEulerAngles(_headRotation * glm::quat(glm::radians(glm::vec3(
averageEyePitch, averageEyeYaw, 0.0f))));
// smooth relative to the window
const float LONG_TERM_AVERAGE_SMOOTHING = 0.999f; const float LONG_TERM_AVERAGE_SMOOTHING = 0.999f;
_longTermAverageEyePitch = glm::mix(averageEyePitch, _longTermAverageEyePitch, LONG_TERM_AVERAGE_SMOOTHING); _longTermAverageEyePitch = glm::mix(eyeEulers.x, _longTermAverageEyePitch, LONG_TERM_AVERAGE_SMOOTHING);
_longTermAverageEyeYaw = glm::mix(averageEyeYaw, _longTermAverageEyeYaw, LONG_TERM_AVERAGE_SMOOTHING); _longTermAverageEyeYaw = glm::mix(eyeEulers.y, _longTermAverageEyeYaw, LONG_TERM_AVERAGE_SMOOTHING);
_estimatedEyePitch = averageEyePitch - _longTermAverageEyePitch;
_estimatedEyeYaw = averageEyeYaw - _longTermAverageEyeYaw; // back to head-relative
float windowEyePitch = eyeEulers.x - _longTermAverageEyePitch;
float windowEyeYaw = eyeEulers.y - _longTermAverageEyeYaw;
glm::vec3 relativeEyeEulers = safeEulerAngles(glm::inverse(_headRotation) * glm::quat(glm::radians(glm::vec3(
windowEyePitch, windowEyeYaw, 0.0f))));
_estimatedEyePitch = relativeEyeEulers.x;
_estimatedEyeYaw = relativeEyeEulers.y;
} }
void Faceshift::reset() { void Faceshift::reset() {