diff --git a/interface/src/Avatar.cpp b/interface/src/Avatar.cpp index 64b9310b78..4b9a35733a 100644 --- a/interface/src/Avatar.cpp +++ b/interface/src/Avatar.cpp @@ -47,9 +47,8 @@ const float HEAD_MAX_PITCH = 45; const float HEAD_MIN_PITCH = -45; const float HEAD_MAX_YAW = 85; const float HEAD_MIN_YAW = -85; -const float AVATAR_BRAKING_RANGE = 1.6f; -const float AVATAR_BRAKING_STRENGTH = 30.0f; -//const float MAX_JOINT_TOUCH_DOT = 0.995f; +const float AVATAR_BRAKING_RANGE = 1.3f; +const float AVATAR_BRAKING_STRENGTH = 40.0f; const float JOINT_TOUCH_RANGE = 0.0005f; float skinColor [] = {1.0, 0.84, 0.66}; @@ -105,7 +104,7 @@ Avatar::Avatar(bool isMine) { initializeSkeleton(); - _avatarTouch.setReachableRadius(0.6); + _avatarTouch.setReachableRadius(1.0); if (BALLS_ON) { _balls = new Balls(100); } else { _balls = NULL; } @@ -880,13 +879,7 @@ void Avatar::render(bool lookingInMirror, glm::vec3 cameraPosition) { //render body renderBody(lookingInMirror); - - /* - // render head - if (_displayingHead) { - _head.render(lookingInMirror, _bodyYaw); - } - */ + // if this is my avatar, then render my interactions with the other avatar if (_isMine) { @@ -1407,7 +1400,6 @@ void Avatar::processTransmitterData(unsigned char* packetData, int numBytes) { angularVelocity = glm::vec3(glm::degrees(gyrY), glm::degrees(-gyrX), glm::degrees(-gyrZ)); setHeadFromGyros(&eulerAngles, &angularVelocity, (_transmitterHz == 0.f) ? 0.f : 1.f / _transmitterHz, 1000.0); - } } diff --git a/interface/src/Camera.cpp b/interface/src/Camera.cpp index 4cd66521f0..2a74de363b 100644 --- a/interface/src/Camera.cpp +++ b/interface/src/Camera.cpp @@ -12,13 +12,14 @@ #include "Camera.h" -const float MODE_SHIFT_RATE = 5.0f; +const float MODE_SHIFT_RATE = 6.0f; Camera::Camera() { _needsToInitialize = true; _frustumNeedsReshape = true; + _modeShift = 0.0; _mode = CAMERA_MODE_THIRD_PERSON; _tightness = 10.0; // default _fieldOfView = 60.0; // default @@ -41,6 +42,10 @@ Camera::Camera() { _attributes[m].upShift = 0.0f; _attributes[m].distance = 0.0f; _attributes[m].tightness = 0.0f; + + _previousAttributes[m].upShift = 0.0f; + _previousAttributes[m].distance = 0.0f; + _previousAttributes[m].tightness = 0.0f; } } @@ -68,6 +73,13 @@ void Camera::generateOrientation() { // use iterative forces to keep the camera at the desired position and angle void Camera::updateFollowMode(float deltaTime) { + if (_modeShift < 1.0f) { + _modeShift += 5.0f * deltaTime; + if (_modeShift > 1.0f ) { + _modeShift = 1.0f; + } + } + // derive t from tightness float t = _tightness * deltaTime; if (t > 1.0) { @@ -106,15 +118,29 @@ void Camera::updateFollowMode(float deltaTime) { // force position towards ideal position _position += (_idealPosition - _position) * t; } + + float mm = 1.0f - _modeShift; + _upShift = _attributes[_mode].upShift * _modeShift + _previousAttributes[_mode].upShift * mm; + _distance = _attributes[_mode].distance * _modeShift + _previousAttributes[_mode].distance * mm; + _upShift = _attributes[_mode].upShift * _modeShift + _previousAttributes[_mode].upShift * mm; + + /* //transition to the attributes of the current mode _upShift += (_attributes[_mode].upShift - _upShift ) * deltaTime * MODE_SHIFT_RATE; _distance += (_attributes[_mode].distance - _distance ) * deltaTime * MODE_SHIFT_RATE; _tightness += (_attributes[_mode].tightness - _tightness) * deltaTime * MODE_SHIFT_RATE; + */ + } + void Camera::setMode(CameraMode m, CameraFollowingAttributes a) { + _previousAttributes[m].upShift = _attributes[m].upShift; + _previousAttributes[m].distance = _attributes[m].distance; + _previousAttributes[m].tightness = _attributes[m].tightness; + _attributes[m].upShift = a.upShift; _attributes[m].distance = a.distance; _attributes[m].tightness = a.tightness; @@ -124,7 +150,7 @@ void Camera::setMode(CameraMode m, CameraFollowingAttributes a) { void Camera::setMode(CameraMode m) { _mode = m; - _needsToInitialize = true; + _modeShift = 0.0; } void Camera::setTargetRotation( float yaw, float pitch, float roll ) { @@ -155,6 +181,7 @@ void Camera::setFarClip (float f) { void Camera::initialize() { _needsToInitialize = true; + _modeShift = 0.0; } // call to find out if the view frustum needs to be reshaped diff --git a/interface/src/Camera.h b/interface/src/Camera.h index 52c577e88a..348bde0d89 100644 --- a/interface/src/Camera.h +++ b/interface/src/Camera.h @@ -89,8 +89,10 @@ private: float _distance; float _tightness; Orientation _orientation; + float _modeShift; CameraFollowingAttributes _attributes[NUM_CAMERA_MODES]; + CameraFollowingAttributes _previousAttributes[NUM_CAMERA_MODES]; void generateOrientation(); void updateFollowMode( float deltaTime ); diff --git a/interface/src/Head.cpp b/interface/src/Head.cpp index 6cdc9a7c7a..51d3e42c3f 100644 --- a/interface/src/Head.cpp +++ b/interface/src/Head.cpp @@ -222,8 +222,6 @@ void Head::simulate(float deltaTime, bool isMine) { } - - void Head::render(bool lookingInMirror, float bodyYaw) { int side = 0; @@ -268,7 +266,6 @@ void Head::render(bool lookingInMirror, float bodyYaw) { audioAttack = 0.9 * audioAttack + 0.1 * fabs(audioLoudness - lastLoudness); lastLoudness = audioLoudness; - const float BROW_LIFT_THRESHOLD = 100; if (audioAttack > BROW_LIFT_THRESHOLD) browAudioLift += sqrt(audioAttack) / 1000.0; @@ -295,20 +292,23 @@ void Head::render(bool lookingInMirror, float bodyYaw) { glPushMatrix(); glTranslatef(0,-0.35,0.75); glColor3f(0,0,0); + glRotatef(mouthPitch, 1, 0, 0); glRotatef(mouthYaw, 0, 0, 1); + if (averageLoudness > 1.f) { - glScalef(mouthWidth * (.7f + sqrt(averageLoudness) /60.f), + glScalef(mouthWidth * (.7f + sqrt(averageLoudness) /60.f), mouthHeight * (1.f + sqrt(averageLoudness) /30.f), 1); } else { glScalef(mouthWidth, mouthHeight, 1); - } + } glutSolidCube(0.5); glPopMatrix(); glTranslatef(0, 1.0, 0); + glTranslatef(-interPupilDistance/2.0,-0.68,0.7); // Right Eye glRotatef(-10, 1, 0, 0); @@ -373,6 +373,5 @@ void Head::render(bool lookingInMirror, float bodyYaw) { glPopMatrix(); glPopMatrix(); - } diff --git a/interface/src/Head.h b/interface/src/Head.h index 3d345d5140..ee12098e24 100644 --- a/interface/src/Head.h +++ b/interface/src/Head.h @@ -37,57 +37,54 @@ public: float getAverageLoudness() {return averageLoudness;}; void setAverageLoudness(float al) { averageLoudness = al;}; + + bool returnHeadToCenter; + float audioLoudness; + glm::vec3 skinColor; + glm::vec3 position; + glm::vec3 rotation; + float yaw; + float pitch; + float roll; + float pitchRate; + float yawRate; + float rollRate; + float noise; + float eyeballPitch[2]; + float eyeballYaw [2]; + float eyebrowPitch[2]; + float eyebrowRoll [2]; + float eyeballScaleX; + float eyeballScaleY; + float eyeballScaleZ; + float interPupilDistance; + float interBrowDistance; + float nominalPupilSize; + float pupilSize; + float mouthPitch; + float mouthYaw; + float mouthWidth; + float mouthHeight; + float leanForward; + float leanSideways; + float pitchTarget; + float yawTarget; + float noiseEnvelope; + float pupilConverge; + float scale; + int eyeContact; + float browAudioLift; + eyeContactTargets eyeContactTarget; -//private: -// I am making these public for now - just to get the code moved over quickly! + // Sound loudness information + float lastLoudness; + float averageLoudness; + float audioAttack; + + GLUquadric* sphere; - bool returnHeadToCenter; - float audioLoudness; - glm::vec3 skinColor; - glm::vec3 position; - glm::vec3 rotation; - float yaw; - float pitch; - float roll; - float pitchRate; - float yawRate; - float rollRate; - float noise; - float eyeballPitch[2]; - float eyeballYaw [2]; - float eyebrowPitch[2]; - float eyebrowRoll [2]; - float eyeballScaleX; - float eyeballScaleY; - float eyeballScaleZ; - float interPupilDistance; - float interBrowDistance; - float nominalPupilSize; - float pupilSize; - float mouthPitch; - float mouthYaw; - float mouthWidth; - float mouthHeight; - float leanForward; - float leanSideways; - float pitchTarget; - float yawTarget; - float noiseEnvelope; - float pupilConverge; - float scale; - int eyeContact; - float browAudioLift; - eyeContactTargets eyeContactTarget; - - // Sound loudness information - float lastLoudness; - float averageLoudness; - float audioAttack; - - GLUquadric* sphere; - - // Strength of return springs - float returnSpringScale; + // Strength of return springs + float returnSpringScale; }; #endif diff --git a/interface/src/main.cpp b/interface/src/main.cpp index f606fab416..ff3cd22034 100644 --- a/interface/src/main.cpp +++ b/interface/src/main.cpp @@ -97,7 +97,6 @@ int packetsPerSecond = 0; int bytesPerSecond = 0; int bytesCount = 0; - int screenWidth = 1200; // Window size int screenHeight = 800; @@ -339,6 +338,7 @@ void init(void) { a.distance = 1.5f; a.tightness = 8.0f; myCamera.setMode(CAMERA_MODE_THIRD_PERSON, a); + myCamera.initialize(); myAvatar.setDisplayingHead(true); OculusManager::connect(); @@ -1046,7 +1046,7 @@ void display(void) glPushMatrix(); { glLoadIdentity(); - + // camera settings if (OculusManager::isConnected()) { myAvatar.setDisplayingHead(false); @@ -1063,13 +1063,14 @@ void display(void) } else { if (myCamera.getMode() == CAMERA_MODE_FIRST_PERSON) { myCamera.setTargetPosition(myAvatar.getSpringyHeadPosition()); - myCamera.setTargetRotation(myAvatar.getAbsoluteHeadYaw()- mouseViewShiftYaw, myAvatar.getRenderPitch() + mouseViewShiftPitch, 0.0f); + myCamera.setTargetRotation(myAvatar.getAbsoluteHeadYaw()- mouseViewShiftYaw, -20.0f + myAvatar.getRenderPitch() + mouseViewShiftPitch, 0.0f); } else if (myCamera.getMode() == CAMERA_MODE_THIRD_PERSON) { + myCamera.setTargetPosition(myAvatar.getHeadPosition()); myCamera.setTargetRotation(myAvatar.getBodyYaw() - mouseViewShiftYaw, mouseViewShiftPitch, 0.0f); } } - + // important... myCamera.update( 1.f/FPS ); @@ -1081,7 +1082,7 @@ void display(void) glTranslatef(1, 1, HUD_Z_OFFSET); drawVector(&test); glPopMatrix(); - */ + */ // Note: whichCamera is used to pick between the normal camera myCamera for our @@ -1240,6 +1241,7 @@ int setRenderFirstPerson(int state) { bool value = setValue(state, &::renderFirstPersonOn); if (state == MENU_ROW_PICKED) { if (::renderFirstPersonOn) { + Camera::CameraFollowingAttributes a; a.upShift = 0.0f; a.distance = 0.0f; @@ -1870,14 +1872,34 @@ void idle(void) { ::mouseVoxel.green = ::mouseVoxel.blue = 0; } } - - // walking triggers the handControl to stop + + // when walking handControl stops if (myAvatar.getMode() == AVATAR_MODE_WALKING) { handControl.stop(); mouseViewShiftYaw *= 0.9; mouseViewShiftPitch *= 0.9; } + if (myCamera.getMode() != CAMERA_MODE_MIRROR) { + if (myAvatar.getIsNearInteractingOther()) { + myAvatar.setDisplayingHead(false); + Camera::CameraFollowingAttributes a; + a.upShift = 0.0f; + a.distance = 0.0f; + a.tightness = 100.0f; + myCamera.setMode(CAMERA_MODE_FIRST_PERSON, a); + } else { + if (myCamera.getMode() != CAMERA_MODE_THIRD_PERSON) { + myAvatar.setDisplayingHead(true); + Camera::CameraFollowingAttributes a; + a.upShift = -0.2f; + a.distance = 1.5f; + a.tightness = 8.0f; + myCamera.setMode(CAMERA_MODE_THIRD_PERSON, a); + } + } + } + // Read serial port interface devices if (serialPort.active) { serialPort.readData();