From 905670ae7fc3fcbe206953467505df9f2b2abd71 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 16 Jul 2014 15:41:46 -0700 Subject: [PATCH 01/14] Added files for FaceshiftScriptingInterface --- .../src/FaceshiftScriptingInterface.cpp | 18 ++++++++++++ .../src/FaceshiftScriptingInterface.h | 29 +++++++++++++++++++ 2 files changed, 47 insertions(+) create mode 100644 libraries/animation/src/FaceshiftScriptingInterface.cpp create mode 100644 libraries/animation/src/FaceshiftScriptingInterface.h diff --git a/libraries/animation/src/FaceshiftScriptingInterface.cpp b/libraries/animation/src/FaceshiftScriptingInterface.cpp new file mode 100644 index 0000000000..0dd191c18b --- /dev/null +++ b/libraries/animation/src/FaceshiftScriptingInterface.cpp @@ -0,0 +1,18 @@ +// +// FaceshiftScriptingInterface.cpp +// interface/src/scripting +// +// Created by Ben Arnold on 7/38/14. +// Copyright 2014 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +#include "Application.h" +#include "FaceshiftScriptingInterface.h" + +FaceshiftScriptingInterface* FaceshiftScriptingInterface::getInstance() { + static FaceshiftScriptingInterface sharedInstance; + return &sharedInstance; +} \ No newline at end of file diff --git a/libraries/animation/src/FaceshiftScriptingInterface.h b/libraries/animation/src/FaceshiftScriptingInterface.h new file mode 100644 index 0000000000..b365f66df6 --- /dev/null +++ b/libraries/animation/src/FaceshiftScriptingInterface.h @@ -0,0 +1,29 @@ +// +// FaceshiftScriptingInterface.h +// interface/src/scripting +// +// Created by Ben Arnold on 7/38/14. +// Copyright 2014 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +#ifndef hifi_FaceshiftScriptingInterface_h +#define hifi_FaceshiftScriptingInterface_h + +#include +#include +#include + +class FaceshiftScriptingInterface : public QObject { + Q_OBJECT + FaceshiftScriptingInterface() { }; +public: + static FaceshiftScriptingInterface* getInstance(); + + public slots: + +}; + +#endif // hifi_FaceshiftScriptingInterface_h From 88de5949a4c19d39609d651667c551263c34daed Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 16 Jul 2014 16:34:30 -0700 Subject: [PATCH 02/14] Fleshed out FaceshiftScriptingInterface --- interface/src/Application.cpp | 2 + .../src/FaceshiftScriptingInterface.cpp | 89 +++++++++++++++++++ .../src/FaceshiftScriptingInterface.h | 36 +++++++- 3 files changed, 125 insertions(+), 2 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index bc6db5d7b6..045d54291e 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -70,6 +70,7 @@ #include "Menu.h" #include "ModelUploader.h" #include "Util.h" +#include "FaceshiftScriptingInterface.h" #include "devices/MIDIManager.h" #include "devices/OculusManager.h" #include "devices/TV3DManager.h" @@ -3638,6 +3639,7 @@ ScriptEngine* Application::loadScript(const QString& scriptName, bool loadScript scriptEngine->registerGlobalObject("Menu", MenuScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("Settings", SettingsScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("AudioDevice", AudioDeviceScriptingInterface::getInstance()); + scriptEngine->registerGlobalObject("Faceshift", FaceshiftScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("AnimationCache", &_animationCache); scriptEngine->registerGlobalObject("AudioReflector", &_audioReflector); scriptEngine->registerGlobalObject("Account", AccountScriptingInterface::getInstance()); diff --git a/libraries/animation/src/FaceshiftScriptingInterface.cpp b/libraries/animation/src/FaceshiftScriptingInterface.cpp index 0dd191c18b..64118f0f2f 100644 --- a/libraries/animation/src/FaceshiftScriptingInterface.cpp +++ b/libraries/animation/src/FaceshiftScriptingInterface.cpp @@ -15,4 +15,93 @@ FaceshiftScriptingInterface* FaceshiftScriptingInterface::getInstance() { static FaceshiftScriptingInterface sharedInstance; return &sharedInstance; +} + + +bool FaceshiftScriptingInterface::isConnectedOrConnecting() const { + return Application::getInstance()->getFaceshift()->isConnectedOrConnecting(); +} + +bool FaceshiftScriptingInterface::isActive() const { + return Application::getInstance()->getFaceshift()->isActive(); +} + +const glm::vec3& FaceshiftScriptingInterface::getHeadAngularVelocity() const { + return Application::getInstance()->getFaceshift()->getHeadAngularVelocity(); +} + +// these pitch/yaw angles are in degrees +float FaceshiftScriptingInterface::getEyeGazeLeftPitch() const { + return Application::getInstance()->getFaceshift()->getEyeGazeLeftPitch(); +} +float FaceshiftScriptingInterface::getEyeGazeLeftYaw() const { + return Application::getInstance()->getFaceshift()->getEyeGazeLeftYaw(); +} + +float FaceshiftScriptingInterface::getEyeGazeRightPitch() const { + return Application::getInstance()->getFaceshift()->getEyeGazeRightPitch(); +} +float FaceshiftScriptingInterface::getEyeGazeRightYaw() const { + return Application::getInstance()->getFaceshift()->getEyeGazeRightYaw(); +} + +float FaceshiftScriptingInterface::getLeftBlink() const { + return Application::getInstance()->getFaceshift()->getLeftBlink(); +} + +float FaceshiftScriptingInterface::getRightBlink() const { + return Application::getInstance()->getFaceshift()->getRightBlink(); +} + +float FaceshiftScriptingInterface::getLeftEyeOpen() const { + return Application::getInstance()->getFaceshift()->getLeftEyeOpen(); +} + +float FaceshiftScriptingInterface::getRightEyeOpen() const { + return Application::getInstance()->getFaceshift()->getRightEyeOpen(); +} + +float FaceshiftScriptingInterface::getBrowDownLeft() const { + return Application::getInstance()->getFaceshift()->getBrowDownLeft(); +} + +float FaceshiftScriptingInterface::getBrowDownRight() const { + return Application::getInstance()->getFaceshift()->getBrowDownRight(); +} + +float FaceshiftScriptingInterface::getBrowUpCenter() const { + return Application::getInstance()->getFaceshift()->getBrowUpCenter(); +} + +float FaceshiftScriptingInterface::getBrowUpLeft() const { + return Application::getInstance()->getFaceshift()->getBrowUpLeft(); +} + +float FaceshiftScriptingInterface::getBrowUpRight() const { + return Application::getInstance()->getFaceshift()->getBrowUpRight(); +} + +float FaceshiftScriptingInterface::getMouthSize() const { + return Application::getInstance()->getFaceshift()->getMouthSize(); +} + +float FaceshiftScriptingInterface::getMouthSmileLeft() const { + return Application::getInstance()->getFaceshift()->getMouthSmileLeft(); +} + +float FaceshiftScriptingInterface::getMouthSmileRight() const { + return Application::getInstance()->getFaceshift()->getMouthSmileRight(); +} + +void FaceshiftScriptingInterface::update() { + Application::getInstance()->getFaceshift()->update(); +} + +void FaceshiftScriptingInterface::reset() { + Application::getInstance()->getFaceshift()->reset; +} + +void FaceshiftScriptingInterface::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen, QVector& coefficients) const { + Application::getInstance()->getFaceshift()->updateFakeCoefficients(leftBlink, rightBlink, browUp, jawOpen, coefficients); } \ No newline at end of file diff --git a/libraries/animation/src/FaceshiftScriptingInterface.h b/libraries/animation/src/FaceshiftScriptingInterface.h index b365f66df6..f52dd953fa 100644 --- a/libraries/animation/src/FaceshiftScriptingInterface.h +++ b/libraries/animation/src/FaceshiftScriptingInterface.h @@ -22,8 +22,40 @@ class FaceshiftScriptingInterface : public QObject { public: static FaceshiftScriptingInterface* getInstance(); - public slots: - +public slots: + bool isConnectedOrConnecting() const; + + bool isActive() const; + + const glm::vec3& getHeadAngularVelocity() const; + + // these pitch/yaw angles are in degrees + float getEyeGazeLeftPitch() const; + float getEyeGazeLeftYaw() const; + + float getEyeGazeRightPitch() const; + float getEyeGazeRightYaw() const; + + float getLeftBlink() const; + float getRightBlink() const; + float getLeftEyeOpen() const; + float getRightEyeOpen() const; + + float getBrowDownLeft() const; + float getBrowDownRight() const; + float getBrowUpCenter() const; + float getBrowUpLeft() const; + float getBrowUpRight() const; + + float getMouthSize() const; + float getMouthSmileLeft() const; + float getMouthSmileRight() const; + + void update(); + void reset(); + + void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen, QVector& coefficients) const; }; #endif // hifi_FaceshiftScriptingInterface_h From 90dc3cf5de918405de811333d041e8c911c90700 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 16 Jul 2014 18:24:03 -0700 Subject: [PATCH 03/14] Small changes --- libraries/animation/src/FaceshiftScriptingInterface.cpp | 4 +--- libraries/animation/src/FaceshiftScriptingInterface.h | 2 ++ 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/libraries/animation/src/FaceshiftScriptingInterface.cpp b/libraries/animation/src/FaceshiftScriptingInterface.cpp index 64118f0f2f..7de217e7d1 100644 --- a/libraries/animation/src/FaceshiftScriptingInterface.cpp +++ b/libraries/animation/src/FaceshiftScriptingInterface.cpp @@ -9,7 +9,6 @@ // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // -#include "Application.h" #include "FaceshiftScriptingInterface.h" FaceshiftScriptingInterface* FaceshiftScriptingInterface::getInstance() { @@ -17,7 +16,6 @@ FaceshiftScriptingInterface* FaceshiftScriptingInterface::getInstance() { return &sharedInstance; } - bool FaceshiftScriptingInterface::isConnectedOrConnecting() const { return Application::getInstance()->getFaceshift()->isConnectedOrConnecting(); } @@ -98,7 +96,7 @@ void FaceshiftScriptingInterface::update() { } void FaceshiftScriptingInterface::reset() { - Application::getInstance()->getFaceshift()->reset; + Application::getInstance()->getFaceshift()->reset(); } void FaceshiftScriptingInterface::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, diff --git a/libraries/animation/src/FaceshiftScriptingInterface.h b/libraries/animation/src/FaceshiftScriptingInterface.h index f52dd953fa..3d7a6000e5 100644 --- a/libraries/animation/src/FaceshiftScriptingInterface.h +++ b/libraries/animation/src/FaceshiftScriptingInterface.h @@ -16,6 +16,8 @@ #include #include +#include "Application.h" + class FaceshiftScriptingInterface : public QObject { Q_OBJECT FaceshiftScriptingInterface() { }; From 192fe71ac464259e826062640449c6dd88ef7398 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Mon, 21 Jul 2014 14:24:05 -0700 Subject: [PATCH 04/14] removed faceShiftScriptingInterface --- interface/src/Application.cpp | 2 - .../src/FaceshiftScriptingInterface.cpp | 105 ------------------ .../src/FaceshiftScriptingInterface.h | 63 ----------- 3 files changed, 170 deletions(-) delete mode 100644 libraries/animation/src/FaceshiftScriptingInterface.cpp delete mode 100644 libraries/animation/src/FaceshiftScriptingInterface.h diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 045d54291e..bc6db5d7b6 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -70,7 +70,6 @@ #include "Menu.h" #include "ModelUploader.h" #include "Util.h" -#include "FaceshiftScriptingInterface.h" #include "devices/MIDIManager.h" #include "devices/OculusManager.h" #include "devices/TV3DManager.h" @@ -3639,7 +3638,6 @@ ScriptEngine* Application::loadScript(const QString& scriptName, bool loadScript scriptEngine->registerGlobalObject("Menu", MenuScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("Settings", SettingsScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("AudioDevice", AudioDeviceScriptingInterface::getInstance()); - scriptEngine->registerGlobalObject("Faceshift", FaceshiftScriptingInterface::getInstance()); scriptEngine->registerGlobalObject("AnimationCache", &_animationCache); scriptEngine->registerGlobalObject("AudioReflector", &_audioReflector); scriptEngine->registerGlobalObject("Account", AccountScriptingInterface::getInstance()); diff --git a/libraries/animation/src/FaceshiftScriptingInterface.cpp b/libraries/animation/src/FaceshiftScriptingInterface.cpp deleted file mode 100644 index 7de217e7d1..0000000000 --- a/libraries/animation/src/FaceshiftScriptingInterface.cpp +++ /dev/null @@ -1,105 +0,0 @@ -// -// FaceshiftScriptingInterface.cpp -// interface/src/scripting -// -// Created by Ben Arnold on 7/38/14. -// Copyright 2014 High Fidelity, Inc. -// -// Distributed under the Apache License, Version 2.0. -// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// - -#include "FaceshiftScriptingInterface.h" - -FaceshiftScriptingInterface* FaceshiftScriptingInterface::getInstance() { - static FaceshiftScriptingInterface sharedInstance; - return &sharedInstance; -} - -bool FaceshiftScriptingInterface::isConnectedOrConnecting() const { - return Application::getInstance()->getFaceshift()->isConnectedOrConnecting(); -} - -bool FaceshiftScriptingInterface::isActive() const { - return Application::getInstance()->getFaceshift()->isActive(); -} - -const glm::vec3& FaceshiftScriptingInterface::getHeadAngularVelocity() const { - return Application::getInstance()->getFaceshift()->getHeadAngularVelocity(); -} - -// these pitch/yaw angles are in degrees -float FaceshiftScriptingInterface::getEyeGazeLeftPitch() const { - return Application::getInstance()->getFaceshift()->getEyeGazeLeftPitch(); -} -float FaceshiftScriptingInterface::getEyeGazeLeftYaw() const { - return Application::getInstance()->getFaceshift()->getEyeGazeLeftYaw(); -} - -float FaceshiftScriptingInterface::getEyeGazeRightPitch() const { - return Application::getInstance()->getFaceshift()->getEyeGazeRightPitch(); -} -float FaceshiftScriptingInterface::getEyeGazeRightYaw() const { - return Application::getInstance()->getFaceshift()->getEyeGazeRightYaw(); -} - -float FaceshiftScriptingInterface::getLeftBlink() const { - return Application::getInstance()->getFaceshift()->getLeftBlink(); -} - -float FaceshiftScriptingInterface::getRightBlink() const { - return Application::getInstance()->getFaceshift()->getRightBlink(); -} - -float FaceshiftScriptingInterface::getLeftEyeOpen() const { - return Application::getInstance()->getFaceshift()->getLeftEyeOpen(); -} - -float FaceshiftScriptingInterface::getRightEyeOpen() const { - return Application::getInstance()->getFaceshift()->getRightEyeOpen(); -} - -float FaceshiftScriptingInterface::getBrowDownLeft() const { - return Application::getInstance()->getFaceshift()->getBrowDownLeft(); -} - -float FaceshiftScriptingInterface::getBrowDownRight() const { - return Application::getInstance()->getFaceshift()->getBrowDownRight(); -} - -float FaceshiftScriptingInterface::getBrowUpCenter() const { - return Application::getInstance()->getFaceshift()->getBrowUpCenter(); -} - -float FaceshiftScriptingInterface::getBrowUpLeft() const { - return Application::getInstance()->getFaceshift()->getBrowUpLeft(); -} - -float FaceshiftScriptingInterface::getBrowUpRight() const { - return Application::getInstance()->getFaceshift()->getBrowUpRight(); -} - -float FaceshiftScriptingInterface::getMouthSize() const { - return Application::getInstance()->getFaceshift()->getMouthSize(); -} - -float FaceshiftScriptingInterface::getMouthSmileLeft() const { - return Application::getInstance()->getFaceshift()->getMouthSmileLeft(); -} - -float FaceshiftScriptingInterface::getMouthSmileRight() const { - return Application::getInstance()->getFaceshift()->getMouthSmileRight(); -} - -void FaceshiftScriptingInterface::update() { - Application::getInstance()->getFaceshift()->update(); -} - -void FaceshiftScriptingInterface::reset() { - Application::getInstance()->getFaceshift()->reset(); -} - -void FaceshiftScriptingInterface::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen, QVector& coefficients) const { - Application::getInstance()->getFaceshift()->updateFakeCoefficients(leftBlink, rightBlink, browUp, jawOpen, coefficients); -} \ No newline at end of file diff --git a/libraries/animation/src/FaceshiftScriptingInterface.h b/libraries/animation/src/FaceshiftScriptingInterface.h deleted file mode 100644 index 3d7a6000e5..0000000000 --- a/libraries/animation/src/FaceshiftScriptingInterface.h +++ /dev/null @@ -1,63 +0,0 @@ -// -// FaceshiftScriptingInterface.h -// interface/src/scripting -// -// Created by Ben Arnold on 7/38/14. -// Copyright 2014 High Fidelity, Inc. -// -// Distributed under the Apache License, Version 2.0. -// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// - -#ifndef hifi_FaceshiftScriptingInterface_h -#define hifi_FaceshiftScriptingInterface_h - -#include -#include -#include - -#include "Application.h" - -class FaceshiftScriptingInterface : public QObject { - Q_OBJECT - FaceshiftScriptingInterface() { }; -public: - static FaceshiftScriptingInterface* getInstance(); - -public slots: - bool isConnectedOrConnecting() const; - - bool isActive() const; - - const glm::vec3& getHeadAngularVelocity() const; - - // these pitch/yaw angles are in degrees - float getEyeGazeLeftPitch() const; - float getEyeGazeLeftYaw() const; - - float getEyeGazeRightPitch() const; - float getEyeGazeRightYaw() const; - - float getLeftBlink() const; - float getRightBlink() const; - float getLeftEyeOpen() const; - float getRightEyeOpen() const; - - float getBrowDownLeft() const; - float getBrowDownRight() const; - float getBrowUpCenter() const; - float getBrowUpLeft() const; - float getBrowUpRight() const; - - float getMouthSize() const; - float getMouthSmileLeft() const; - float getMouthSmileRight() const; - - void update(); - void reset(); - - void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen, QVector& coefficients) const; -}; - -#endif // hifi_FaceshiftScriptingInterface_h From fc9fb11e4f6039f5c70bf0e00de2f4c82984929f Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Tue, 22 Jul 2014 11:56:19 -0700 Subject: [PATCH 05/14] Added FacialAnimationData class --- examples/bot.js | 2 +- interface/src/devices/Faceshift.cpp | 50 ++++++-------- interface/src/devices/Faceshift.h | 43 +++++------- .../animation/src/FacialAnimationData.cpp | 30 +++++++++ libraries/animation/src/FacialAnimationData.h | 65 +++++++++++++++++++ 5 files changed, 130 insertions(+), 60 deletions(-) create mode 100644 libraries/animation/src/FacialAnimationData.cpp create mode 100644 libraries/animation/src/FacialAnimationData.h diff --git a/examples/bot.js b/examples/bot.js index e42d234abf..edef280e21 100644 --- a/examples/bot.js +++ b/examples/bot.js @@ -92,7 +92,7 @@ function playRandomSound() { botNumber = getRandomInt(1, 100); if (botNumber <= 20) { - newFaceFilePrefix = "bot" + botNumber; + newFaceFilePrefix = "amber"; newBodyFilePrefix = "defaultAvatar_body" } else { if (botNumber <= 40) { diff --git a/interface/src/devices/Faceshift.cpp b/interface/src/devices/Faceshift.cpp index a7d50814e2..4105b17652 100644 --- a/interface/src/devices/Faceshift.cpp +++ b/interface/src/devices/Faceshift.cpp @@ -32,18 +32,6 @@ Faceshift::Faceshift() : _eyeGazeLeftYaw(0.0f), _eyeGazeRightPitch(0.0f), _eyeGazeRightYaw(0.0f), - _leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes - _rightBlinkIndex(1), - _leftEyeOpenIndex(8), - _rightEyeOpenIndex(9), - _browDownLeftIndex(14), - _browDownRightIndex(15), - _browUpCenterIndex(16), - _browUpLeftIndex(17), - _browUpRightIndex(18), - _mouthSmileLeftIndex(28), - _mouthSmileRightIndex(29), - _jawOpenIndex(21), _longTermAverageEyePitch(0.0f), _longTermAverageEyeYaw(0.0f), _longTermAverageInitialized(false) @@ -107,14 +95,14 @@ void Faceshift::reset() { void Faceshift::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen, QVector& coefficients) const { - coefficients.resize(max((int)coefficients.size(), _jawOpenIndex + 1)); + coefficients.resize(max((int)coefficients.size(), _facialAnimationData._jawOpenIndex + 1)); qFill(coefficients.begin(), coefficients.end(), 0.0f); - coefficients[_leftBlinkIndex] = leftBlink; - coefficients[_rightBlinkIndex] = rightBlink; - coefficients[_browUpCenterIndex] = browUp; - coefficients[_browUpLeftIndex] = browUp; - coefficients[_browUpRightIndex] = browUp; - coefficients[_jawOpenIndex] = jawOpen; + coefficients[_facialAnimationData._leftBlinkIndex] = leftBlink; + coefficients[_facialAnimationData._rightBlinkIndex] = rightBlink; + coefficients[_facialAnimationData._browUpCenterIndex] = browUp; + coefficients[_facialAnimationData._browUpLeftIndex] = browUp; + coefficients[_facialAnimationData._browUpRightIndex] = browUp; + coefficients[_facialAnimationData._jawOpenIndex] = jawOpen; } void Faceshift::setTCPEnabled(bool enabled) { @@ -217,40 +205,40 @@ void Faceshift::receive(const QByteArray& buffer) { const vector& names = static_cast(msg.get())->blendshape_names(); for (size_t i = 0; i < names.size(); i++) { if (names[i] == "EyeBlink_L") { - _leftBlinkIndex = i; + _facialAnimationData._leftBlinkIndex = i; } else if (names[i] == "EyeBlink_R") { - _rightBlinkIndex = i; + _facialAnimationData._rightBlinkIndex = i; } else if (names[i] == "EyeOpen_L") { - _leftEyeOpenIndex = i; + _facialAnimationData._leftEyeOpenIndex = i; } else if (names[i] == "EyeOpen_R") { - _rightEyeOpenIndex = i; + _facialAnimationData._rightEyeOpenIndex = i; } else if (names[i] == "BrowsD_L") { - _browDownLeftIndex = i; + _facialAnimationData._browDownLeftIndex = i; } else if (names[i] == "BrowsD_R") { - _browDownRightIndex = i; + _facialAnimationData._browDownRightIndex = i; } else if (names[i] == "BrowsU_C") { - _browUpCenterIndex = i; + _facialAnimationData._browUpCenterIndex = i; } else if (names[i] == "BrowsU_L") { - _browUpLeftIndex = i; + _facialAnimationData._browUpLeftIndex = i; } else if (names[i] == "BrowsU_R") { - _browUpRightIndex = i; + _facialAnimationData._browUpRightIndex = i; } else if (names[i] == "JawOpen") { - _jawOpenIndex = i; + _facialAnimationData._jawOpenIndex = i; } else if (names[i] == "MouthSmile_L") { - _mouthSmileLeftIndex = i; + _facialAnimationData._mouthSmileLeftIndex = i; } else if (names[i] == "MouthSmile_R") { - _mouthSmileRightIndex = i; + _facialAnimationData._mouthSmileRightIndex = i; } } break; diff --git a/interface/src/devices/Faceshift.h b/interface/src/devices/Faceshift.h index 2fc1aaddb1..87fd1076ee 100644 --- a/interface/src/devices/Faceshift.h +++ b/interface/src/devices/Faceshift.h @@ -18,6 +18,7 @@ #include #include "FaceTracker.h" +#include "FacialAnimationData.h" /// Handles interaction with the Faceshift software, which provides head position/orientation and facial features. class Faceshift : public FaceTracker { @@ -42,20 +43,20 @@ public: float getEyeGazeRightPitch() const { return _eyeGazeRightPitch; } float getEyeGazeRightYaw() const { return _eyeGazeRightYaw; } - float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } - float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } - float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } - float getRightEyeOpen() const { return getBlendshapeCoefficient(_rightEyeOpenIndex); } + float getLeftBlink() const { return getBlendshapeCoefficient(_facialAnimationData._leftBlinkIndex); } + float getRightBlink() const { return getBlendshapeCoefficient(_facialAnimationData._rightBlinkIndex); } + float getLeftEyeOpen() const { return getBlendshapeCoefficient(_facialAnimationData._leftEyeOpenIndex); } + float getRightEyeOpen() const { return getBlendshapeCoefficient(_facialAnimationData._rightEyeOpenIndex); } - float getBrowDownLeft() const { return getBlendshapeCoefficient(_browDownLeftIndex); } - float getBrowDownRight() const { return getBlendshapeCoefficient(_browDownRightIndex); } - float getBrowUpCenter() const { return getBlendshapeCoefficient(_browUpCenterIndex); } - float getBrowUpLeft() const { return getBlendshapeCoefficient(_browUpLeftIndex); } - float getBrowUpRight() const { return getBlendshapeCoefficient(_browUpRightIndex); } + float getBrowDownLeft() const { return getBlendshapeCoefficient(_facialAnimationData._browDownLeftIndex); } + float getBrowDownRight() const { return getBlendshapeCoefficient(_facialAnimationData._browDownRightIndex); } + float getBrowUpCenter() const { return getBlendshapeCoefficient(_facialAnimationData._browUpCenterIndex); } + float getBrowUpLeft() const { return getBlendshapeCoefficient(_facialAnimationData._browUpLeftIndex); } + float getBrowUpRight() const { return getBlendshapeCoefficient(_facialAnimationData._browUpRightIndex); } - float getMouthSize() const { return getBlendshapeCoefficient(_jawOpenIndex); } - float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } - float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } + float getMouthSize() const { return getBlendshapeCoefficient(_facialAnimationData._jawOpenIndex); } + float getMouthSmileLeft() const { return getBlendshapeCoefficient(_facialAnimationData._mouthSmileLeftIndex); } + float getMouthSmileRight() const { return getBlendshapeCoefficient(_facialAnimationData._mouthSmileRightIndex); } void update(); void reset(); @@ -102,23 +103,9 @@ private: float _eyeGazeRightPitch; float _eyeGazeRightYaw; - int _leftBlinkIndex; - int _rightBlinkIndex; - int _leftEyeOpenIndex; - int _rightEyeOpenIndex; + // stores blendshape indexes + FacialAnimationData _facialAnimationData; - // Brows - int _browDownLeftIndex; - int _browDownRightIndex; - int _browUpCenterIndex; - int _browUpLeftIndex; - int _browUpRightIndex; - - int _mouthSmileLeftIndex; - int _mouthSmileRightIndex; - - int _jawOpenIndex; - // degrees float _longTermAverageEyePitch; float _longTermAverageEyeYaw; diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp new file mode 100644 index 0000000000..0f45675083 --- /dev/null +++ b/libraries/animation/src/FacialAnimationData.cpp @@ -0,0 +1,30 @@ +// +// FacialAnimationData.cpp +// interface/src/devices +// +// Created by Ben Arnold on 7/21/2014. +// Copyright 2014 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +#include "FacialAnimationData.h" + +FacialAnimationData::FacialAnimationData() :_leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes +_rightBlinkIndex(1), +_leftEyeOpenIndex(8), +_rightEyeOpenIndex(9), +_browDownLeftIndex(14), +_browDownRightIndex(15), +_browUpCenterIndex(16), +_browUpLeftIndex(17), +_browUpRightIndex(18), +_mouthSmileLeftIndex(28), +_mouthSmileRightIndex(29), +_jawOpenIndex(21) { +} + +float FacialAnimationData::getBlendshapeCoefficient(int index) const { + return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; +} \ No newline at end of file diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h new file mode 100644 index 0000000000..c8d740c1c9 --- /dev/null +++ b/libraries/animation/src/FacialAnimationData.h @@ -0,0 +1,65 @@ +// +// FacialAnimationData.h +// interface/src/devices +// +// Created by Ben Arnold on 7/21/2014. +// Copyright 2014 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +#ifndef hifi_FacialAnimationData_h +#define hifi_FacialAnimationData_h + +#include +#include + +/// Stores facial animation data for use by faceshift or scripts +class FacialAnimationData : public QObject { + Q_OBJECT + +public: + friend class Faceshift; + + FacialAnimationData(); + + float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } + float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } + float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } + float getRightEyeOpen() const { return getBlendshapeCoefficient(_rightEyeOpenIndex); } + + float getBrowDownLeft() const { return getBlendshapeCoefficient(_browDownLeftIndex); } + float getBrowDownRight() const { return getBlendshapeCoefficient(_browDownRightIndex); } + float getBrowUpCenter() const { return getBlendshapeCoefficient(_browUpCenterIndex); } + float getBrowUpLeft() const { return getBlendshapeCoefficient(_browUpLeftIndex); } + float getBrowUpRight() const { return getBlendshapeCoefficient(_browUpRightIndex); } + + float getMouthSize() const { return getBlendshapeCoefficient(_jawOpenIndex); } + float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } + float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } + +private: + float getBlendshapeCoefficient(int index) const; + + int _leftBlinkIndex; + int _rightBlinkIndex; + int _leftEyeOpenIndex; + int _rightEyeOpenIndex; + + int _browDownLeftIndex; + int _browDownRightIndex; + int _browUpCenterIndex; + int _browUpLeftIndex; + int _browUpRightIndex; + + int _mouthSmileLeftIndex; + int _mouthSmileRightIndex; + + int _jawOpenIndex; + + //Only used by agents, since FaceTracker has its own _blendshapeCoefficients; + QVector _blendshapeCoefficients; +}; + +#endif // hifi_FacialAnimationData_h \ No newline at end of file From f3ae2280302f5e6da31202f9f01d44babd262927 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Tue, 22 Jul 2014 13:46:29 -0700 Subject: [PATCH 06/14] Moved some FaceShift stuff to FacialAnimationData. Made use of FacialAnimationData --- interface/src/avatar/Head.cpp | 11 +++++------ interface/src/devices/Faceshift.cpp | 12 ------------ interface/src/devices/Faceshift.h | 3 --- libraries/animation/src/FacialAnimationData.cpp | 16 ++++++++++++++++ libraries/animation/src/FacialAnimationData.h | 8 +++++++- libraries/avatars/src/AvatarData.cpp | 16 ++++++++++------ libraries/avatars/src/AvatarData.h | 5 +++++ libraries/avatars/src/HeadData.cpp | 6 ++++++ libraries/avatars/src/HeadData.h | 10 ++++++++-- 9 files changed, 57 insertions(+), 30 deletions(-) diff --git a/interface/src/avatar/Head.cpp b/interface/src/avatar/Head.cpp index ee242d179a..814377b3d2 100644 --- a/interface/src/avatar/Head.cpp +++ b/interface/src/avatar/Head.cpp @@ -66,7 +66,7 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { if (isMine) { FaceTracker* faceTracker = Application::getInstance()->getActiveFaceTracker(); if ((_isFaceshiftConnected = faceTracker)) { - _blendshapeCoefficients = faceTracker->getBlendshapeCoefficients(); + _facialAnimationData->setBlendshapeCoefficients(faceTracker->getBlendshapeCoefficients()); _isFaceshiftConnected = true; } } @@ -141,11 +141,10 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { // use data to update fake Faceshift blendshape coefficients const float JAW_OPEN_SCALE = 10.f; - Application::getInstance()->getFaceshift()->updateFakeCoefficients(_leftEyeBlink, - _rightEyeBlink, - _browAudioLift, - glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f), - _blendshapeCoefficients); + _facialAnimationData->updateFakeCoefficients(_leftEyeBlink, + _rightEyeBlink, + _browAudioLift, + glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f)); } if (!isMine) { diff --git a/interface/src/devices/Faceshift.cpp b/interface/src/devices/Faceshift.cpp index 4105b17652..40ee12af86 100644 --- a/interface/src/devices/Faceshift.cpp +++ b/interface/src/devices/Faceshift.cpp @@ -93,18 +93,6 @@ void Faceshift::reset() { _longTermAverageInitialized = false; } -void Faceshift::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen, QVector& coefficients) const { - coefficients.resize(max((int)coefficients.size(), _facialAnimationData._jawOpenIndex + 1)); - qFill(coefficients.begin(), coefficients.end(), 0.0f); - coefficients[_facialAnimationData._leftBlinkIndex] = leftBlink; - coefficients[_facialAnimationData._rightBlinkIndex] = rightBlink; - coefficients[_facialAnimationData._browUpCenterIndex] = browUp; - coefficients[_facialAnimationData._browUpLeftIndex] = browUp; - coefficients[_facialAnimationData._browUpRightIndex] = browUp; - coefficients[_facialAnimationData._jawOpenIndex] = jawOpen; -} - void Faceshift::setTCPEnabled(bool enabled) { if ((_tcpEnabled = enabled)) { connectSocket(); diff --git a/interface/src/devices/Faceshift.h b/interface/src/devices/Faceshift.h index 87fd1076ee..2b720c843d 100644 --- a/interface/src/devices/Faceshift.h +++ b/interface/src/devices/Faceshift.h @@ -61,9 +61,6 @@ public: void update(); void reset(); - void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen, QVector& coefficients) const; - signals: void connectionStateChanged(); diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp index 0f45675083..974cdec66f 100644 --- a/libraries/animation/src/FacialAnimationData.cpp +++ b/libraries/animation/src/FacialAnimationData.cpp @@ -11,6 +11,10 @@ #include "FacialAnimationData.h" +#ifndef max +inline int max(int a, int b) { return a > b ? a : b; } +#endif + FacialAnimationData::FacialAnimationData() :_leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes _rightBlinkIndex(1), _leftEyeOpenIndex(8), @@ -27,4 +31,16 @@ _jawOpenIndex(21) { float FacialAnimationData::getBlendshapeCoefficient(int index) const { return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; +} + +void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen) { + _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); + qFill(_blendshapeCoefficients.begin(), _blendshapeCoefficients.end(), 0.0f); + _blendshapeCoefficients[_leftBlinkIndex] = leftBlink; + _blendshapeCoefficients[_rightBlinkIndex] = rightBlink; + _blendshapeCoefficients[_browUpCenterIndex] = browUp; + _blendshapeCoefficients[_browUpLeftIndex] = browUp; + _blendshapeCoefficients[_browUpRightIndex] = browUp; + _blendshapeCoefficients[_jawOpenIndex] = jawOpen; } \ No newline at end of file diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h index c8d740c1c9..514fd5a55f 100644 --- a/libraries/animation/src/FacialAnimationData.h +++ b/libraries/animation/src/FacialAnimationData.h @@ -21,6 +21,8 @@ class FacialAnimationData : public QObject { public: friend class Faceshift; + friend class HeadData; + friend class AvatarData; FacialAnimationData(); @@ -39,6 +41,11 @@ public: float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } + void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen); + + void setBlendshapeCoefficients(const QVector& coefficients) { _blendshapeCoefficients = coefficients; } + const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } + private: float getBlendshapeCoefficient(int index) const; @@ -58,7 +65,6 @@ private: int _jawOpenIndex; - //Only used by agents, since FaceTracker has its own _blendshapeCoefficients; QVector _blendshapeCoefficients; }; diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index 6cfa4ba488..fc5b762a0f 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -29,6 +29,8 @@ #include "AvatarData.h" +#include "../animation/src/FacialAnimationData.h" + quint64 DEFAULT_FILTERED_LOG_EXPIRY = 2 * USECS_PER_SECOND; using namespace std; @@ -151,10 +153,12 @@ QByteArray AvatarData::toByteArray() { memcpy(destinationBuffer, &_headData->_browAudioLift, sizeof(float)); destinationBuffer += sizeof(float); - *destinationBuffer++ = _headData->_blendshapeCoefficients.size(); - memcpy(destinationBuffer, _headData->_blendshapeCoefficients.data(), - _headData->_blendshapeCoefficients.size() * sizeof(float)); - destinationBuffer += _headData->_blendshapeCoefficients.size() * sizeof(float); + const QVector& blendshapeCoefficients = _headData->_facialAnimationData->getBlendshapeCoefficients(); + + *destinationBuffer++ = blendshapeCoefficients.size(); + memcpy(destinationBuffer, blendshapeCoefficients.data(), + blendshapeCoefficients.size() * sizeof(float)); + destinationBuffer += blendshapeCoefficients.size() * sizeof(float); } // pupil dilation @@ -429,8 +433,8 @@ int AvatarData::parseDataAtOffset(const QByteArray& packet, int offset) { return maxAvailableSize; } - _headData->_blendshapeCoefficients.resize(numCoefficients); - memcpy(_headData->_blendshapeCoefficients.data(), sourceBuffer, blendDataSize); + _headData->_facialAnimationData->_blendshapeCoefficients.resize(numCoefficients); + memcpy(_headData->_facialAnimationData->_blendshapeCoefficients.data(), sourceBuffer, blendDataSize); sourceBuffer += numCoefficients * sizeof(float); //bitItemsDataSize = 4 * sizeof(float) + 1 + blendDataSize; diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index 1b8f6e6007..b1b48e3941 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -206,6 +206,11 @@ public: Q_INVOKABLE virtual QStringList getJointNames() const { return _jointNames; } + // Facial Animation + Q_INVOKABLE void setLeftEyebrow(float f) { + _headData->setLeftEyebrow(f); + } + // key state void setKeyState(KeyState s) { _keyState = s; } KeyState keyState() const { return _keyState; } diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index c691a2c28a..1f2bb73834 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -16,6 +16,8 @@ #include "AvatarData.h" #include "HeadData.h" +#include "../animation/src/FacialAnimationData.h" + HeadData::HeadData(AvatarData* owningAvatar) : _baseYaw(0.0f), _basePitch(0.0f), @@ -29,6 +31,7 @@ HeadData::HeadData(AvatarData* owningAvatar) : _rightEyeBlink(0.0f), _averageLoudness(0.0f), _browAudioLift(0.0f), + _facialAnimationData(new FacialAnimationData), _owningAvatar(owningAvatar) { @@ -64,3 +67,6 @@ void HeadData::addRoll(float roll) { setBaseRoll(_baseRoll + roll); } +const QVector& HeadData::getBlendshapeCoefficients() const { + return _facialAnimationData->_blendshapeCoefficients; +} \ No newline at end of file diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index 9e2920ae85..9920776b2a 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -28,6 +28,7 @@ const float MIN_HEAD_ROLL = -50.f; const float MAX_HEAD_ROLL = 50.f; class AvatarData; +class FacialAnimationData; class HeadData { public: @@ -54,11 +55,16 @@ public: float getAudioAverageLoudness() const { return _audioAverageLoudness; } void setAudioAverageLoudness(float audioAverageLoudness) { _audioAverageLoudness = audioAverageLoudness; } - const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } + const QVector& getBlendshapeCoefficients() const; float getPupilDilation() const { return _pupilDilation; } void setPupilDilation(float pupilDilation) { _pupilDilation = pupilDilation; } + // Facial animation + void setLeftEyebrow(float f) { + + } + // degrees void addYaw(float yaw); void addPitch(float pitch); @@ -85,7 +91,7 @@ protected: float _averageLoudness; float _browAudioLift; float _audioAverageLoudness; - QVector _blendshapeCoefficients; + FacialAnimationData* _facialAnimationData; float _pupilDilation; AvatarData* _owningAvatar; From 512034fd7cb5f10ef3123218210a3f873b43d82a Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 15:23:27 -0700 Subject: [PATCH 07/14] Ability to modify AC avatar blendshapes from JS --- assignment-client/src/Agent.cpp | 7 ++- examples/bot.js | 15 ++++-- interface/src/avatar/Head.cpp | 2 +- .../animation/src/FacialAnimationData.cpp | 10 +++- libraries/animation/src/FacialAnimationData.h | 18 +++++++ libraries/avatars/src/AvatarData.cpp | 5 ++ libraries/avatars/src/AvatarData.h | 18 +++++-- libraries/avatars/src/HeadData.cpp | 49 +++++++++++++++++++ libraries/avatars/src/HeadData.h | 15 +++++- 9 files changed, 125 insertions(+), 14 deletions(-) diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp index 0449e0d682..0f485dec14 100644 --- a/assignment-client/src/Agent.cpp +++ b/assignment-client/src/Agent.cpp @@ -229,11 +229,13 @@ void Agent::run() { // setup an Avatar for the script to use AvatarData scriptedAvatar; - + // Pretend faceshift is active so we can modify facial data + scriptedAvatar.setIsFaceshiftConnected(true); + // call model URL setters with empty URLs so our avatar, if user, will have the default models scriptedAvatar.setFaceModelURL(QUrl()); scriptedAvatar.setSkeletonModelURL(QUrl()); - + // give this AvatarData object to the script engine _scriptEngine.setAvatarData(&scriptedAvatar, "Avatar"); _scriptEngine.setAvatarHashMap(&_avatarHashMap, "AvatarList"); @@ -263,6 +265,7 @@ void Agent::run() { _scriptEngine.getModelsScriptingInterface()->setModelTree(_modelViewer.getTree()); _scriptEngine.setScriptContents(scriptContents); + _scriptEngine.run(); setFinished(true); } diff --git a/examples/bot.js b/examples/bot.js index edef280e21..1c8fd218d9 100644 --- a/examples/bot.js +++ b/examples/bot.js @@ -24,11 +24,11 @@ function printVector(string, vector) { print(string + " " + vector.x + ", " + vector.y + ", " + vector.z); } -var CHANCE_OF_MOVING = 0.005; -var CHANCE_OF_SOUND = 0.005; +var CHANCE_OF_MOVING = 0.0; +var CHANCE_OF_SOUND = 0.0; var CHANCE_OF_HEAD_TURNING = 0.05; -var CHANCE_OF_BIG_MOVE = 0.1; -var CHANCE_OF_WAVING = 0.009; +var CHANCE_OF_BIG_MOVE = 0.0; +var CHANCE_OF_WAVING = 0.0; var shouldReceiveVoxels = true; var VOXEL_FPS = 60.0; @@ -147,6 +147,13 @@ function updateBehavior(deltaTime) { if (CHANCE_OF_MOVING == 0.000) { Avatar.position = firstPosition; } + //print("hi"); + Avatar.setLeftBlink(1.0); + Avatar.setRightBlink(0.5); + Avatar.setBrowDownLeft(1.0); + Avatar.setMouthSize(1.0); + Avatar.setMouthSmileRight(1.0); + //print("ho"); if (shouldReceiveVoxels && ((cumulativeTime - lastVoxelQueryTime) > (1.0 / VOXEL_FPS))) { VoxelViewer.setPosition(Avatar.position); diff --git a/interface/src/avatar/Head.cpp b/interface/src/avatar/Head.cpp index 814377b3d2..244eaab8ab 100644 --- a/interface/src/avatar/Head.cpp +++ b/interface/src/avatar/Head.cpp @@ -146,7 +146,7 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { _browAudioLift, glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f)); } - + if (!isMine) { _faceModel.setLODDistance(static_cast(_owningAvatar)->getLODDistance()); } diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp index 974cdec66f..68e61bbe72 100644 --- a/libraries/animation/src/FacialAnimationData.cpp +++ b/libraries/animation/src/FacialAnimationData.cpp @@ -29,12 +29,18 @@ _mouthSmileRightIndex(29), _jawOpenIndex(21) { } +void FacialAnimationData::setBlendshapeCoefficient(int index, float val) { + _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); + if (index >= 0 && index < (int)_blendshapeCoefficients.size()) { + _blendshapeCoefficients[index] = val; + } +} + float FacialAnimationData::getBlendshapeCoefficient(int index) const { return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; } -void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen) { +void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen) { _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); qFill(_blendshapeCoefficients.begin(), _blendshapeCoefficients.end(), 0.0f); _blendshapeCoefficients[_leftBlinkIndex] = leftBlink; diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h index 514fd5a55f..f87f3a9748 100644 --- a/libraries/animation/src/FacialAnimationData.h +++ b/libraries/animation/src/FacialAnimationData.h @@ -26,6 +26,23 @@ public: FacialAnimationData(); + // Setters + void setLeftBlink(float val) { setBlendshapeCoefficient(_leftBlinkIndex, val); } + void setRightBlink(float val) { setBlendshapeCoefficient(_rightBlinkIndex, val); } + void setLeftEyeOpen(float val) { setBlendshapeCoefficient(_leftBlinkIndex, val); } + void setRightEyeOpen(float val) { setBlendshapeCoefficient(_rightBlinkIndex, val); } + + void setBrowDownLeft(float val) { setBlendshapeCoefficient(_browDownLeftIndex, val); } + void setBrowDownRight(float val) { setBlendshapeCoefficient(_browDownRightIndex, val); } + void setBrowUpCenter(float val) { setBlendshapeCoefficient(_browUpCenterIndex, val); } + void setBrowUpLeft(float val) { setBlendshapeCoefficient(_browUpLeftIndex, val); } + void setBrowUpRight(float val) { setBlendshapeCoefficient(_browUpRightIndex, val); } + + void setMouthSize(float val) { setBlendshapeCoefficient(_jawOpenIndex, val); } + void setMouthSmileLeft(float val) { setBlendshapeCoefficient(_mouthSmileLeftIndex, val); } + void setMouthSmileRight(float val) { setBlendshapeCoefficient(_mouthSmileRightIndex, val); } + + // Getters float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } @@ -47,6 +64,7 @@ public: const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } private: + void setBlendshapeCoefficient(int index, float val); float getBlendshapeCoefficient(int index) const; int _leftBlinkIndex; diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index fc5b762a0f..93186eb78a 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -45,6 +45,7 @@ AvatarData::AvatarData() : _handState(0), _keyState(NO_KEY_DOWN), _isChatCirclingEnabled(false), + _forceFaceshiftIsConnected(false), _hasNewJointRotations(true), _headData(NULL), _handData(NULL), @@ -82,6 +83,10 @@ QByteArray AvatarData::toByteArray() { // lazily allocate memory for HeadData in case we're not an Avatar instance if (!_headData) { _headData = new HeadData(this); + // In some cases, for instance for AC avatars, we might want to force faceshift to appear connected + if (_forceFaceshiftIsConnected) { + _headData->setIsFaceshiftConnected(true); + } } QByteArray avatarDataByteArray; diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index b1b48e3941..33fbd39616 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -207,9 +207,20 @@ public: Q_INVOKABLE virtual QStringList getJointNames() const { return _jointNames; } // Facial Animation - Q_INVOKABLE void setLeftEyebrow(float f) { - _headData->setLeftEyebrow(f); - } + Q_INVOKABLE void setLeftBlink(float val) { _headData->setLeftBlink(val); } + Q_INVOKABLE void setRightBlink(float val) { _headData->setRightBlink(val); } + Q_INVOKABLE void setLeftEyeOpen(float val) { _headData->setLeftEyeOpen(val); } + Q_INVOKABLE void setRightEyeOpen(float val) { _headData->setRightEyeOpen(val); } + Q_INVOKABLE void setBrowDownLeft(float val) { _headData->setBrowDownLeft(val); } + Q_INVOKABLE void setBrowDownRight(float val) { _headData->setBrowDownRight(val); } + Q_INVOKABLE void setBrowUpCenter(float val) { _headData->setBrowUpCenter(val); } + Q_INVOKABLE void setBrowUpLeft(float val) { _headData->setBrowUpLeft(val); } + Q_INVOKABLE void setBrowUpRight(float val) { _headData->setBrowUpRight(val); } + Q_INVOKABLE void setMouthSize(float val) { _headData->setMouthSize(val); } + Q_INVOKABLE void setMouthSmileLeft(float val) { _headData->setMouthSmileLeft(val); } + Q_INVOKABLE void setMouthSmileRight(float val) { _headData->setMouthSmileRight(val); } + + void setIsFaceshiftConnected(bool isFaceshift) { _forceFaceshiftIsConnected = isFaceshift; } // key state void setKeyState(KeyState s) { _keyState = s; } @@ -305,6 +316,7 @@ protected: std::string _chatMessage; bool _isChatCirclingEnabled; + bool _forceFaceshiftIsConnected; bool _hasNewJointRotations; // set in AvatarData, cleared in Avatar diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index 1f2bb73834..919adcd642 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -55,6 +55,55 @@ void HeadData::setOrientation(const glm::quat& orientation) { _baseRoll = eulers.z; } +void HeadData::setLeftBlink(float val) { + _facialAnimationData->setLeftBlink(val); +} + +void HeadData::setRightBlink(float val) { + _facialAnimationData->setRightBlink(val); +} + +void HeadData::setLeftEyeOpen(float val) { + _facialAnimationData->setLeftEyeOpen(val); +} + +void HeadData::setRightEyeOpen(float val) { + _facialAnimationData->setRightEyeOpen(val); +} + +void HeadData::setBrowDownLeft(float val) { + _facialAnimationData->setBrowDownLeft(val); +} + +void HeadData::setBrowDownRight(float val) { + _facialAnimationData->setBrowDownRight(val); +} + +void HeadData::setBrowUpCenter(float val) { + _facialAnimationData->setBrowUpCenter(val); +} + +void HeadData::setBrowUpLeft(float val) { + _facialAnimationData->setBrowUpLeft(val); +} + +void HeadData::setBrowUpRight(float val) { + _facialAnimationData->setBrowUpRight(val); +} + +void HeadData::setMouthSize(float val) { + _facialAnimationData->setMouthSize(val); +} + +void HeadData::setMouthSmileLeft(float val) { + _facialAnimationData->setLeftBlink(val); +} + +void HeadData::setMouthSmileRight(float val) { + _facialAnimationData->setMouthSmileRight(val); +} + + void HeadData::addYaw(float yaw) { setBaseYaw(_baseYaw + yaw); } diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index 9920776b2a..b6e877564a 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -61,9 +61,20 @@ public: void setPupilDilation(float pupilDilation) { _pupilDilation = pupilDilation; } // Facial animation - void setLeftEyebrow(float f) { + void setLeftBlink(float val); + void setRightBlink(float val); + void setLeftEyeOpen(float val); + void setRightEyeOpen(float val); + void setBrowDownLeft(float val); + void setBrowDownRight(float val); + void setBrowUpCenter(float val); + void setBrowUpLeft(float val); + void setBrowUpRight(float val); + void setMouthSize(float val); + void setMouthSmileLeft(float val); + void setMouthSmileRight(float val); - } + void setIsFaceshiftConnected(bool isFaceshiftConnected) { _isFaceshiftConnected = isFaceshiftConnected; } // degrees void addYaw(float yaw); From 6aa9e6b7367ee4a95d339512a2106ced04c99326 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 15:54:40 -0700 Subject: [PATCH 08/14] Revert "Ability to modify AC avatar blendshapes from JS" This reverts commit 512034fd7cb5f10ef3123218210a3f873b43d82a. --- assignment-client/src/Agent.cpp | 7 +-- examples/bot.js | 15 ++---- interface/src/avatar/Head.cpp | 2 +- .../animation/src/FacialAnimationData.cpp | 10 +--- libraries/animation/src/FacialAnimationData.h | 18 ------- libraries/avatars/src/AvatarData.cpp | 5 -- libraries/avatars/src/AvatarData.h | 18 ++----- libraries/avatars/src/HeadData.cpp | 49 ------------------- libraries/avatars/src/HeadData.h | 15 +----- 9 files changed, 14 insertions(+), 125 deletions(-) diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp index 0f485dec14..0449e0d682 100644 --- a/assignment-client/src/Agent.cpp +++ b/assignment-client/src/Agent.cpp @@ -229,13 +229,11 @@ void Agent::run() { // setup an Avatar for the script to use AvatarData scriptedAvatar; - // Pretend faceshift is active so we can modify facial data - scriptedAvatar.setIsFaceshiftConnected(true); - + // call model URL setters with empty URLs so our avatar, if user, will have the default models scriptedAvatar.setFaceModelURL(QUrl()); scriptedAvatar.setSkeletonModelURL(QUrl()); - + // give this AvatarData object to the script engine _scriptEngine.setAvatarData(&scriptedAvatar, "Avatar"); _scriptEngine.setAvatarHashMap(&_avatarHashMap, "AvatarList"); @@ -265,7 +263,6 @@ void Agent::run() { _scriptEngine.getModelsScriptingInterface()->setModelTree(_modelViewer.getTree()); _scriptEngine.setScriptContents(scriptContents); - _scriptEngine.run(); setFinished(true); } diff --git a/examples/bot.js b/examples/bot.js index 1c8fd218d9..edef280e21 100644 --- a/examples/bot.js +++ b/examples/bot.js @@ -24,11 +24,11 @@ function printVector(string, vector) { print(string + " " + vector.x + ", " + vector.y + ", " + vector.z); } -var CHANCE_OF_MOVING = 0.0; -var CHANCE_OF_SOUND = 0.0; +var CHANCE_OF_MOVING = 0.005; +var CHANCE_OF_SOUND = 0.005; var CHANCE_OF_HEAD_TURNING = 0.05; -var CHANCE_OF_BIG_MOVE = 0.0; -var CHANCE_OF_WAVING = 0.0; +var CHANCE_OF_BIG_MOVE = 0.1; +var CHANCE_OF_WAVING = 0.009; var shouldReceiveVoxels = true; var VOXEL_FPS = 60.0; @@ -147,13 +147,6 @@ function updateBehavior(deltaTime) { if (CHANCE_OF_MOVING == 0.000) { Avatar.position = firstPosition; } - //print("hi"); - Avatar.setLeftBlink(1.0); - Avatar.setRightBlink(0.5); - Avatar.setBrowDownLeft(1.0); - Avatar.setMouthSize(1.0); - Avatar.setMouthSmileRight(1.0); - //print("ho"); if (shouldReceiveVoxels && ((cumulativeTime - lastVoxelQueryTime) > (1.0 / VOXEL_FPS))) { VoxelViewer.setPosition(Avatar.position); diff --git a/interface/src/avatar/Head.cpp b/interface/src/avatar/Head.cpp index 244eaab8ab..814377b3d2 100644 --- a/interface/src/avatar/Head.cpp +++ b/interface/src/avatar/Head.cpp @@ -146,7 +146,7 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { _browAudioLift, glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f)); } - + if (!isMine) { _faceModel.setLODDistance(static_cast(_owningAvatar)->getLODDistance()); } diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp index 68e61bbe72..974cdec66f 100644 --- a/libraries/animation/src/FacialAnimationData.cpp +++ b/libraries/animation/src/FacialAnimationData.cpp @@ -29,18 +29,12 @@ _mouthSmileRightIndex(29), _jawOpenIndex(21) { } -void FacialAnimationData::setBlendshapeCoefficient(int index, float val) { - _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); - if (index >= 0 && index < (int)_blendshapeCoefficients.size()) { - _blendshapeCoefficients[index] = val; - } -} - float FacialAnimationData::getBlendshapeCoefficient(int index) const { return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; } -void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen) { +void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen) { _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); qFill(_blendshapeCoefficients.begin(), _blendshapeCoefficients.end(), 0.0f); _blendshapeCoefficients[_leftBlinkIndex] = leftBlink; diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h index f87f3a9748..514fd5a55f 100644 --- a/libraries/animation/src/FacialAnimationData.h +++ b/libraries/animation/src/FacialAnimationData.h @@ -26,23 +26,6 @@ public: FacialAnimationData(); - // Setters - void setLeftBlink(float val) { setBlendshapeCoefficient(_leftBlinkIndex, val); } - void setRightBlink(float val) { setBlendshapeCoefficient(_rightBlinkIndex, val); } - void setLeftEyeOpen(float val) { setBlendshapeCoefficient(_leftBlinkIndex, val); } - void setRightEyeOpen(float val) { setBlendshapeCoefficient(_rightBlinkIndex, val); } - - void setBrowDownLeft(float val) { setBlendshapeCoefficient(_browDownLeftIndex, val); } - void setBrowDownRight(float val) { setBlendshapeCoefficient(_browDownRightIndex, val); } - void setBrowUpCenter(float val) { setBlendshapeCoefficient(_browUpCenterIndex, val); } - void setBrowUpLeft(float val) { setBlendshapeCoefficient(_browUpLeftIndex, val); } - void setBrowUpRight(float val) { setBlendshapeCoefficient(_browUpRightIndex, val); } - - void setMouthSize(float val) { setBlendshapeCoefficient(_jawOpenIndex, val); } - void setMouthSmileLeft(float val) { setBlendshapeCoefficient(_mouthSmileLeftIndex, val); } - void setMouthSmileRight(float val) { setBlendshapeCoefficient(_mouthSmileRightIndex, val); } - - // Getters float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } @@ -64,7 +47,6 @@ public: const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } private: - void setBlendshapeCoefficient(int index, float val); float getBlendshapeCoefficient(int index) const; int _leftBlinkIndex; diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index 93186eb78a..fc5b762a0f 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -45,7 +45,6 @@ AvatarData::AvatarData() : _handState(0), _keyState(NO_KEY_DOWN), _isChatCirclingEnabled(false), - _forceFaceshiftIsConnected(false), _hasNewJointRotations(true), _headData(NULL), _handData(NULL), @@ -83,10 +82,6 @@ QByteArray AvatarData::toByteArray() { // lazily allocate memory for HeadData in case we're not an Avatar instance if (!_headData) { _headData = new HeadData(this); - // In some cases, for instance for AC avatars, we might want to force faceshift to appear connected - if (_forceFaceshiftIsConnected) { - _headData->setIsFaceshiftConnected(true); - } } QByteArray avatarDataByteArray; diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index 33fbd39616..b1b48e3941 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -207,20 +207,9 @@ public: Q_INVOKABLE virtual QStringList getJointNames() const { return _jointNames; } // Facial Animation - Q_INVOKABLE void setLeftBlink(float val) { _headData->setLeftBlink(val); } - Q_INVOKABLE void setRightBlink(float val) { _headData->setRightBlink(val); } - Q_INVOKABLE void setLeftEyeOpen(float val) { _headData->setLeftEyeOpen(val); } - Q_INVOKABLE void setRightEyeOpen(float val) { _headData->setRightEyeOpen(val); } - Q_INVOKABLE void setBrowDownLeft(float val) { _headData->setBrowDownLeft(val); } - Q_INVOKABLE void setBrowDownRight(float val) { _headData->setBrowDownRight(val); } - Q_INVOKABLE void setBrowUpCenter(float val) { _headData->setBrowUpCenter(val); } - Q_INVOKABLE void setBrowUpLeft(float val) { _headData->setBrowUpLeft(val); } - Q_INVOKABLE void setBrowUpRight(float val) { _headData->setBrowUpRight(val); } - Q_INVOKABLE void setMouthSize(float val) { _headData->setMouthSize(val); } - Q_INVOKABLE void setMouthSmileLeft(float val) { _headData->setMouthSmileLeft(val); } - Q_INVOKABLE void setMouthSmileRight(float val) { _headData->setMouthSmileRight(val); } - - void setIsFaceshiftConnected(bool isFaceshift) { _forceFaceshiftIsConnected = isFaceshift; } + Q_INVOKABLE void setLeftEyebrow(float f) { + _headData->setLeftEyebrow(f); + } // key state void setKeyState(KeyState s) { _keyState = s; } @@ -316,7 +305,6 @@ protected: std::string _chatMessage; bool _isChatCirclingEnabled; - bool _forceFaceshiftIsConnected; bool _hasNewJointRotations; // set in AvatarData, cleared in Avatar diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index 919adcd642..1f2bb73834 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -55,55 +55,6 @@ void HeadData::setOrientation(const glm::quat& orientation) { _baseRoll = eulers.z; } -void HeadData::setLeftBlink(float val) { - _facialAnimationData->setLeftBlink(val); -} - -void HeadData::setRightBlink(float val) { - _facialAnimationData->setRightBlink(val); -} - -void HeadData::setLeftEyeOpen(float val) { - _facialAnimationData->setLeftEyeOpen(val); -} - -void HeadData::setRightEyeOpen(float val) { - _facialAnimationData->setRightEyeOpen(val); -} - -void HeadData::setBrowDownLeft(float val) { - _facialAnimationData->setBrowDownLeft(val); -} - -void HeadData::setBrowDownRight(float val) { - _facialAnimationData->setBrowDownRight(val); -} - -void HeadData::setBrowUpCenter(float val) { - _facialAnimationData->setBrowUpCenter(val); -} - -void HeadData::setBrowUpLeft(float val) { - _facialAnimationData->setBrowUpLeft(val); -} - -void HeadData::setBrowUpRight(float val) { - _facialAnimationData->setBrowUpRight(val); -} - -void HeadData::setMouthSize(float val) { - _facialAnimationData->setMouthSize(val); -} - -void HeadData::setMouthSmileLeft(float val) { - _facialAnimationData->setLeftBlink(val); -} - -void HeadData::setMouthSmileRight(float val) { - _facialAnimationData->setMouthSmileRight(val); -} - - void HeadData::addYaw(float yaw) { setBaseYaw(_baseYaw + yaw); } diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index b6e877564a..9920776b2a 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -61,20 +61,9 @@ public: void setPupilDilation(float pupilDilation) { _pupilDilation = pupilDilation; } // Facial animation - void setLeftBlink(float val); - void setRightBlink(float val); - void setLeftEyeOpen(float val); - void setRightEyeOpen(float val); - void setBrowDownLeft(float val); - void setBrowDownRight(float val); - void setBrowUpCenter(float val); - void setBrowUpLeft(float val); - void setBrowUpRight(float val); - void setMouthSize(float val); - void setMouthSmileLeft(float val); - void setMouthSmileRight(float val); + void setLeftEyebrow(float f) { - void setIsFaceshiftConnected(bool isFaceshiftConnected) { _isFaceshiftConnected = isFaceshiftConnected; } + } // degrees void addYaw(float yaw); From 7c89201ce8f83720c267f519fba6004ab591bd99 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 15:54:45 -0700 Subject: [PATCH 09/14] Revert "Moved some FaceShift stuff to FacialAnimationData. Made use of" This reverts commit f3ae2280302f5e6da31202f9f01d44babd262927. --- interface/src/avatar/Head.cpp | 11 ++++++----- interface/src/devices/Faceshift.cpp | 12 ++++++++++++ interface/src/devices/Faceshift.h | 3 +++ libraries/animation/src/FacialAnimationData.cpp | 16 ---------------- libraries/animation/src/FacialAnimationData.h | 8 +------- libraries/avatars/src/AvatarData.cpp | 16 ++++++---------- libraries/avatars/src/AvatarData.h | 5 ----- libraries/avatars/src/HeadData.cpp | 6 ------ libraries/avatars/src/HeadData.h | 10 ++-------- 9 files changed, 30 insertions(+), 57 deletions(-) diff --git a/interface/src/avatar/Head.cpp b/interface/src/avatar/Head.cpp index 814377b3d2..ee242d179a 100644 --- a/interface/src/avatar/Head.cpp +++ b/interface/src/avatar/Head.cpp @@ -66,7 +66,7 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { if (isMine) { FaceTracker* faceTracker = Application::getInstance()->getActiveFaceTracker(); if ((_isFaceshiftConnected = faceTracker)) { - _facialAnimationData->setBlendshapeCoefficients(faceTracker->getBlendshapeCoefficients()); + _blendshapeCoefficients = faceTracker->getBlendshapeCoefficients(); _isFaceshiftConnected = true; } } @@ -141,10 +141,11 @@ void Head::simulate(float deltaTime, bool isMine, bool billboard) { // use data to update fake Faceshift blendshape coefficients const float JAW_OPEN_SCALE = 10.f; - _facialAnimationData->updateFakeCoefficients(_leftEyeBlink, - _rightEyeBlink, - _browAudioLift, - glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f)); + Application::getInstance()->getFaceshift()->updateFakeCoefficients(_leftEyeBlink, + _rightEyeBlink, + _browAudioLift, + glm::clamp(log(_averageLoudness) / JAW_OPEN_SCALE, 0.0f, 1.0f), + _blendshapeCoefficients); } if (!isMine) { diff --git a/interface/src/devices/Faceshift.cpp b/interface/src/devices/Faceshift.cpp index 40ee12af86..4105b17652 100644 --- a/interface/src/devices/Faceshift.cpp +++ b/interface/src/devices/Faceshift.cpp @@ -93,6 +93,18 @@ void Faceshift::reset() { _longTermAverageInitialized = false; } +void Faceshift::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen, QVector& coefficients) const { + coefficients.resize(max((int)coefficients.size(), _facialAnimationData._jawOpenIndex + 1)); + qFill(coefficients.begin(), coefficients.end(), 0.0f); + coefficients[_facialAnimationData._leftBlinkIndex] = leftBlink; + coefficients[_facialAnimationData._rightBlinkIndex] = rightBlink; + coefficients[_facialAnimationData._browUpCenterIndex] = browUp; + coefficients[_facialAnimationData._browUpLeftIndex] = browUp; + coefficients[_facialAnimationData._browUpRightIndex] = browUp; + coefficients[_facialAnimationData._jawOpenIndex] = jawOpen; +} + void Faceshift::setTCPEnabled(bool enabled) { if ((_tcpEnabled = enabled)) { connectSocket(); diff --git a/interface/src/devices/Faceshift.h b/interface/src/devices/Faceshift.h index 2b720c843d..87fd1076ee 100644 --- a/interface/src/devices/Faceshift.h +++ b/interface/src/devices/Faceshift.h @@ -61,6 +61,9 @@ public: void update(); void reset(); + void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, + float jawOpen, QVector& coefficients) const; + signals: void connectionStateChanged(); diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp index 974cdec66f..0f45675083 100644 --- a/libraries/animation/src/FacialAnimationData.cpp +++ b/libraries/animation/src/FacialAnimationData.cpp @@ -11,10 +11,6 @@ #include "FacialAnimationData.h" -#ifndef max -inline int max(int a, int b) { return a > b ? a : b; } -#endif - FacialAnimationData::FacialAnimationData() :_leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes _rightBlinkIndex(1), _leftEyeOpenIndex(8), @@ -31,16 +27,4 @@ _jawOpenIndex(21) { float FacialAnimationData::getBlendshapeCoefficient(int index) const { return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; -} - -void FacialAnimationData::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, - float jawOpen) { - _blendshapeCoefficients.resize(max((int)_blendshapeCoefficients.size(), _jawOpenIndex + 1)); - qFill(_blendshapeCoefficients.begin(), _blendshapeCoefficients.end(), 0.0f); - _blendshapeCoefficients[_leftBlinkIndex] = leftBlink; - _blendshapeCoefficients[_rightBlinkIndex] = rightBlink; - _blendshapeCoefficients[_browUpCenterIndex] = browUp; - _blendshapeCoefficients[_browUpLeftIndex] = browUp; - _blendshapeCoefficients[_browUpRightIndex] = browUp; - _blendshapeCoefficients[_jawOpenIndex] = jawOpen; } \ No newline at end of file diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h index 514fd5a55f..c8d740c1c9 100644 --- a/libraries/animation/src/FacialAnimationData.h +++ b/libraries/animation/src/FacialAnimationData.h @@ -21,8 +21,6 @@ class FacialAnimationData : public QObject { public: friend class Faceshift; - friend class HeadData; - friend class AvatarData; FacialAnimationData(); @@ -41,11 +39,6 @@ public: float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } - void updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen); - - void setBlendshapeCoefficients(const QVector& coefficients) { _blendshapeCoefficients = coefficients; } - const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } - private: float getBlendshapeCoefficient(int index) const; @@ -65,6 +58,7 @@ private: int _jawOpenIndex; + //Only used by agents, since FaceTracker has its own _blendshapeCoefficients; QVector _blendshapeCoefficients; }; diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index fc5b762a0f..6cfa4ba488 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -29,8 +29,6 @@ #include "AvatarData.h" -#include "../animation/src/FacialAnimationData.h" - quint64 DEFAULT_FILTERED_LOG_EXPIRY = 2 * USECS_PER_SECOND; using namespace std; @@ -153,12 +151,10 @@ QByteArray AvatarData::toByteArray() { memcpy(destinationBuffer, &_headData->_browAudioLift, sizeof(float)); destinationBuffer += sizeof(float); - const QVector& blendshapeCoefficients = _headData->_facialAnimationData->getBlendshapeCoefficients(); - - *destinationBuffer++ = blendshapeCoefficients.size(); - memcpy(destinationBuffer, blendshapeCoefficients.data(), - blendshapeCoefficients.size() * sizeof(float)); - destinationBuffer += blendshapeCoefficients.size() * sizeof(float); + *destinationBuffer++ = _headData->_blendshapeCoefficients.size(); + memcpy(destinationBuffer, _headData->_blendshapeCoefficients.data(), + _headData->_blendshapeCoefficients.size() * sizeof(float)); + destinationBuffer += _headData->_blendshapeCoefficients.size() * sizeof(float); } // pupil dilation @@ -433,8 +429,8 @@ int AvatarData::parseDataAtOffset(const QByteArray& packet, int offset) { return maxAvailableSize; } - _headData->_facialAnimationData->_blendshapeCoefficients.resize(numCoefficients); - memcpy(_headData->_facialAnimationData->_blendshapeCoefficients.data(), sourceBuffer, blendDataSize); + _headData->_blendshapeCoefficients.resize(numCoefficients); + memcpy(_headData->_blendshapeCoefficients.data(), sourceBuffer, blendDataSize); sourceBuffer += numCoefficients * sizeof(float); //bitItemsDataSize = 4 * sizeof(float) + 1 + blendDataSize; diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index b1b48e3941..1b8f6e6007 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -206,11 +206,6 @@ public: Q_INVOKABLE virtual QStringList getJointNames() const { return _jointNames; } - // Facial Animation - Q_INVOKABLE void setLeftEyebrow(float f) { - _headData->setLeftEyebrow(f); - } - // key state void setKeyState(KeyState s) { _keyState = s; } KeyState keyState() const { return _keyState; } diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index 1f2bb73834..c691a2c28a 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -16,8 +16,6 @@ #include "AvatarData.h" #include "HeadData.h" -#include "../animation/src/FacialAnimationData.h" - HeadData::HeadData(AvatarData* owningAvatar) : _baseYaw(0.0f), _basePitch(0.0f), @@ -31,7 +29,6 @@ HeadData::HeadData(AvatarData* owningAvatar) : _rightEyeBlink(0.0f), _averageLoudness(0.0f), _browAudioLift(0.0f), - _facialAnimationData(new FacialAnimationData), _owningAvatar(owningAvatar) { @@ -67,6 +64,3 @@ void HeadData::addRoll(float roll) { setBaseRoll(_baseRoll + roll); } -const QVector& HeadData::getBlendshapeCoefficients() const { - return _facialAnimationData->_blendshapeCoefficients; -} \ No newline at end of file diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index 9920776b2a..9e2920ae85 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -28,7 +28,6 @@ const float MIN_HEAD_ROLL = -50.f; const float MAX_HEAD_ROLL = 50.f; class AvatarData; -class FacialAnimationData; class HeadData { public: @@ -55,16 +54,11 @@ public: float getAudioAverageLoudness() const { return _audioAverageLoudness; } void setAudioAverageLoudness(float audioAverageLoudness) { _audioAverageLoudness = audioAverageLoudness; } - const QVector& getBlendshapeCoefficients() const; + const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } float getPupilDilation() const { return _pupilDilation; } void setPupilDilation(float pupilDilation) { _pupilDilation = pupilDilation; } - // Facial animation - void setLeftEyebrow(float f) { - - } - // degrees void addYaw(float yaw); void addPitch(float pitch); @@ -91,7 +85,7 @@ protected: float _averageLoudness; float _browAudioLift; float _audioAverageLoudness; - FacialAnimationData* _facialAnimationData; + QVector _blendshapeCoefficients; float _pupilDilation; AvatarData* _owningAvatar; From ba9d89685678ae38433abe45c5b2f4ad340e3921 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 15:54:47 -0700 Subject: [PATCH 10/14] Revert "Added FacialAnimationData class" This reverts commit fc9fb11e4f6039f5c70bf0e00de2f4c82984929f. --- examples/bot.js | 2 +- interface/src/devices/Faceshift.cpp | 50 ++++++++------ interface/src/devices/Faceshift.h | 43 +++++++----- .../animation/src/FacialAnimationData.cpp | 30 --------- libraries/animation/src/FacialAnimationData.h | 65 ------------------- 5 files changed, 60 insertions(+), 130 deletions(-) delete mode 100644 libraries/animation/src/FacialAnimationData.cpp delete mode 100644 libraries/animation/src/FacialAnimationData.h diff --git a/examples/bot.js b/examples/bot.js index edef280e21..e42d234abf 100644 --- a/examples/bot.js +++ b/examples/bot.js @@ -92,7 +92,7 @@ function playRandomSound() { botNumber = getRandomInt(1, 100); if (botNumber <= 20) { - newFaceFilePrefix = "amber"; + newFaceFilePrefix = "bot" + botNumber; newBodyFilePrefix = "defaultAvatar_body" } else { if (botNumber <= 40) { diff --git a/interface/src/devices/Faceshift.cpp b/interface/src/devices/Faceshift.cpp index 4105b17652..a7d50814e2 100644 --- a/interface/src/devices/Faceshift.cpp +++ b/interface/src/devices/Faceshift.cpp @@ -32,6 +32,18 @@ Faceshift::Faceshift() : _eyeGazeLeftYaw(0.0f), _eyeGazeRightPitch(0.0f), _eyeGazeRightYaw(0.0f), + _leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes + _rightBlinkIndex(1), + _leftEyeOpenIndex(8), + _rightEyeOpenIndex(9), + _browDownLeftIndex(14), + _browDownRightIndex(15), + _browUpCenterIndex(16), + _browUpLeftIndex(17), + _browUpRightIndex(18), + _mouthSmileLeftIndex(28), + _mouthSmileRightIndex(29), + _jawOpenIndex(21), _longTermAverageEyePitch(0.0f), _longTermAverageEyeYaw(0.0f), _longTermAverageInitialized(false) @@ -95,14 +107,14 @@ void Faceshift::reset() { void Faceshift::updateFakeCoefficients(float leftBlink, float rightBlink, float browUp, float jawOpen, QVector& coefficients) const { - coefficients.resize(max((int)coefficients.size(), _facialAnimationData._jawOpenIndex + 1)); + coefficients.resize(max((int)coefficients.size(), _jawOpenIndex + 1)); qFill(coefficients.begin(), coefficients.end(), 0.0f); - coefficients[_facialAnimationData._leftBlinkIndex] = leftBlink; - coefficients[_facialAnimationData._rightBlinkIndex] = rightBlink; - coefficients[_facialAnimationData._browUpCenterIndex] = browUp; - coefficients[_facialAnimationData._browUpLeftIndex] = browUp; - coefficients[_facialAnimationData._browUpRightIndex] = browUp; - coefficients[_facialAnimationData._jawOpenIndex] = jawOpen; + coefficients[_leftBlinkIndex] = leftBlink; + coefficients[_rightBlinkIndex] = rightBlink; + coefficients[_browUpCenterIndex] = browUp; + coefficients[_browUpLeftIndex] = browUp; + coefficients[_browUpRightIndex] = browUp; + coefficients[_jawOpenIndex] = jawOpen; } void Faceshift::setTCPEnabled(bool enabled) { @@ -205,40 +217,40 @@ void Faceshift::receive(const QByteArray& buffer) { const vector& names = static_cast(msg.get())->blendshape_names(); for (size_t i = 0; i < names.size(); i++) { if (names[i] == "EyeBlink_L") { - _facialAnimationData._leftBlinkIndex = i; + _leftBlinkIndex = i; } else if (names[i] == "EyeBlink_R") { - _facialAnimationData._rightBlinkIndex = i; + _rightBlinkIndex = i; } else if (names[i] == "EyeOpen_L") { - _facialAnimationData._leftEyeOpenIndex = i; + _leftEyeOpenIndex = i; } else if (names[i] == "EyeOpen_R") { - _facialAnimationData._rightEyeOpenIndex = i; + _rightEyeOpenIndex = i; } else if (names[i] == "BrowsD_L") { - _facialAnimationData._browDownLeftIndex = i; + _browDownLeftIndex = i; } else if (names[i] == "BrowsD_R") { - _facialAnimationData._browDownRightIndex = i; + _browDownRightIndex = i; } else if (names[i] == "BrowsU_C") { - _facialAnimationData._browUpCenterIndex = i; + _browUpCenterIndex = i; } else if (names[i] == "BrowsU_L") { - _facialAnimationData._browUpLeftIndex = i; + _browUpLeftIndex = i; } else if (names[i] == "BrowsU_R") { - _facialAnimationData._browUpRightIndex = i; + _browUpRightIndex = i; } else if (names[i] == "JawOpen") { - _facialAnimationData._jawOpenIndex = i; + _jawOpenIndex = i; } else if (names[i] == "MouthSmile_L") { - _facialAnimationData._mouthSmileLeftIndex = i; + _mouthSmileLeftIndex = i; } else if (names[i] == "MouthSmile_R") { - _facialAnimationData._mouthSmileRightIndex = i; + _mouthSmileRightIndex = i; } } break; diff --git a/interface/src/devices/Faceshift.h b/interface/src/devices/Faceshift.h index 87fd1076ee..2fc1aaddb1 100644 --- a/interface/src/devices/Faceshift.h +++ b/interface/src/devices/Faceshift.h @@ -18,7 +18,6 @@ #include #include "FaceTracker.h" -#include "FacialAnimationData.h" /// Handles interaction with the Faceshift software, which provides head position/orientation and facial features. class Faceshift : public FaceTracker { @@ -43,20 +42,20 @@ public: float getEyeGazeRightPitch() const { return _eyeGazeRightPitch; } float getEyeGazeRightYaw() const { return _eyeGazeRightYaw; } - float getLeftBlink() const { return getBlendshapeCoefficient(_facialAnimationData._leftBlinkIndex); } - float getRightBlink() const { return getBlendshapeCoefficient(_facialAnimationData._rightBlinkIndex); } - float getLeftEyeOpen() const { return getBlendshapeCoefficient(_facialAnimationData._leftEyeOpenIndex); } - float getRightEyeOpen() const { return getBlendshapeCoefficient(_facialAnimationData._rightEyeOpenIndex); } + float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } + float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } + float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } + float getRightEyeOpen() const { return getBlendshapeCoefficient(_rightEyeOpenIndex); } - float getBrowDownLeft() const { return getBlendshapeCoefficient(_facialAnimationData._browDownLeftIndex); } - float getBrowDownRight() const { return getBlendshapeCoefficient(_facialAnimationData._browDownRightIndex); } - float getBrowUpCenter() const { return getBlendshapeCoefficient(_facialAnimationData._browUpCenterIndex); } - float getBrowUpLeft() const { return getBlendshapeCoefficient(_facialAnimationData._browUpLeftIndex); } - float getBrowUpRight() const { return getBlendshapeCoefficient(_facialAnimationData._browUpRightIndex); } + float getBrowDownLeft() const { return getBlendshapeCoefficient(_browDownLeftIndex); } + float getBrowDownRight() const { return getBlendshapeCoefficient(_browDownRightIndex); } + float getBrowUpCenter() const { return getBlendshapeCoefficient(_browUpCenterIndex); } + float getBrowUpLeft() const { return getBlendshapeCoefficient(_browUpLeftIndex); } + float getBrowUpRight() const { return getBlendshapeCoefficient(_browUpRightIndex); } - float getMouthSize() const { return getBlendshapeCoefficient(_facialAnimationData._jawOpenIndex); } - float getMouthSmileLeft() const { return getBlendshapeCoefficient(_facialAnimationData._mouthSmileLeftIndex); } - float getMouthSmileRight() const { return getBlendshapeCoefficient(_facialAnimationData._mouthSmileRightIndex); } + float getMouthSize() const { return getBlendshapeCoefficient(_jawOpenIndex); } + float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } + float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } void update(); void reset(); @@ -103,9 +102,23 @@ private: float _eyeGazeRightPitch; float _eyeGazeRightYaw; - // stores blendshape indexes - FacialAnimationData _facialAnimationData; + int _leftBlinkIndex; + int _rightBlinkIndex; + int _leftEyeOpenIndex; + int _rightEyeOpenIndex; + // Brows + int _browDownLeftIndex; + int _browDownRightIndex; + int _browUpCenterIndex; + int _browUpLeftIndex; + int _browUpRightIndex; + + int _mouthSmileLeftIndex; + int _mouthSmileRightIndex; + + int _jawOpenIndex; + // degrees float _longTermAverageEyePitch; float _longTermAverageEyeYaw; diff --git a/libraries/animation/src/FacialAnimationData.cpp b/libraries/animation/src/FacialAnimationData.cpp deleted file mode 100644 index 0f45675083..0000000000 --- a/libraries/animation/src/FacialAnimationData.cpp +++ /dev/null @@ -1,30 +0,0 @@ -// -// FacialAnimationData.cpp -// interface/src/devices -// -// Created by Ben Arnold on 7/21/2014. -// Copyright 2014 High Fidelity, Inc. -// -// Distributed under the Apache License, Version 2.0. -// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// - -#include "FacialAnimationData.h" - -FacialAnimationData::FacialAnimationData() :_leftBlinkIndex(0), // see http://support.faceshift.com/support/articles/35129-export-of-blendshapes -_rightBlinkIndex(1), -_leftEyeOpenIndex(8), -_rightEyeOpenIndex(9), -_browDownLeftIndex(14), -_browDownRightIndex(15), -_browUpCenterIndex(16), -_browUpLeftIndex(17), -_browUpRightIndex(18), -_mouthSmileLeftIndex(28), -_mouthSmileRightIndex(29), -_jawOpenIndex(21) { -} - -float FacialAnimationData::getBlendshapeCoefficient(int index) const { - return (index >= 0 && index < (int)_blendshapeCoefficients.size()) ? _blendshapeCoefficients[index] : 0.0f; -} \ No newline at end of file diff --git a/libraries/animation/src/FacialAnimationData.h b/libraries/animation/src/FacialAnimationData.h deleted file mode 100644 index c8d740c1c9..0000000000 --- a/libraries/animation/src/FacialAnimationData.h +++ /dev/null @@ -1,65 +0,0 @@ -// -// FacialAnimationData.h -// interface/src/devices -// -// Created by Ben Arnold on 7/21/2014. -// Copyright 2014 High Fidelity, Inc. -// -// Distributed under the Apache License, Version 2.0. -// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// - -#ifndef hifi_FacialAnimationData_h -#define hifi_FacialAnimationData_h - -#include -#include - -/// Stores facial animation data for use by faceshift or scripts -class FacialAnimationData : public QObject { - Q_OBJECT - -public: - friend class Faceshift; - - FacialAnimationData(); - - float getLeftBlink() const { return getBlendshapeCoefficient(_leftBlinkIndex); } - float getRightBlink() const { return getBlendshapeCoefficient(_rightBlinkIndex); } - float getLeftEyeOpen() const { return getBlendshapeCoefficient(_leftEyeOpenIndex); } - float getRightEyeOpen() const { return getBlendshapeCoefficient(_rightEyeOpenIndex); } - - float getBrowDownLeft() const { return getBlendshapeCoefficient(_browDownLeftIndex); } - float getBrowDownRight() const { return getBlendshapeCoefficient(_browDownRightIndex); } - float getBrowUpCenter() const { return getBlendshapeCoefficient(_browUpCenterIndex); } - float getBrowUpLeft() const { return getBlendshapeCoefficient(_browUpLeftIndex); } - float getBrowUpRight() const { return getBlendshapeCoefficient(_browUpRightIndex); } - - float getMouthSize() const { return getBlendshapeCoefficient(_jawOpenIndex); } - float getMouthSmileLeft() const { return getBlendshapeCoefficient(_mouthSmileLeftIndex); } - float getMouthSmileRight() const { return getBlendshapeCoefficient(_mouthSmileRightIndex); } - -private: - float getBlendshapeCoefficient(int index) const; - - int _leftBlinkIndex; - int _rightBlinkIndex; - int _leftEyeOpenIndex; - int _rightEyeOpenIndex; - - int _browDownLeftIndex; - int _browDownRightIndex; - int _browUpCenterIndex; - int _browUpLeftIndex; - int _browUpRightIndex; - - int _mouthSmileLeftIndex; - int _mouthSmileRightIndex; - - int _jawOpenIndex; - - //Only used by agents, since FaceTracker has its own _blendshapeCoefficients; - QVector _blendshapeCoefficients; -}; - -#endif // hifi_FacialAnimationData_h \ No newline at end of file From aba031a1259936eca0bbda55a6ffb72d9b8c33fe Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 16:25:45 -0700 Subject: [PATCH 11/14] Proper blendshape JS api. --- assignment-client/src/Agent.cpp | 3 ++- libraries/avatars/src/AvatarData.cpp | 4 ++++ libraries/avatars/src/AvatarData.h | 6 +++++- libraries/avatars/src/HeadData.cpp | 22 ++++++++++++++++++++++ libraries/avatars/src/HeadData.h | 1 + libraries/fbx/src/FBXReader.cpp | 2 ++ libraries/fbx/src/FBXReader.h | 2 ++ 7 files changed, 38 insertions(+), 2 deletions(-) diff --git a/assignment-client/src/Agent.cpp b/assignment-client/src/Agent.cpp index 0449e0d682..c961d8f19c 100644 --- a/assignment-client/src/Agent.cpp +++ b/assignment-client/src/Agent.cpp @@ -229,7 +229,8 @@ void Agent::run() { // setup an Avatar for the script to use AvatarData scriptedAvatar; - + scriptedAvatar.setForceFaceshiftConnected(true); + // call model URL setters with empty URLs so our avatar, if user, will have the default models scriptedAvatar.setFaceModelURL(QUrl()); scriptedAvatar.setSkeletonModelURL(QUrl()); diff --git a/libraries/avatars/src/AvatarData.cpp b/libraries/avatars/src/AvatarData.cpp index 6cfa4ba488..c3ea2f8b50 100644 --- a/libraries/avatars/src/AvatarData.cpp +++ b/libraries/avatars/src/AvatarData.cpp @@ -43,6 +43,7 @@ AvatarData::AvatarData() : _handState(0), _keyState(NO_KEY_DOWN), _isChatCirclingEnabled(false), + _forceFaceshiftConnected(false), _hasNewJointRotations(true), _headData(NULL), _handData(NULL), @@ -80,6 +81,9 @@ QByteArray AvatarData::toByteArray() { // lazily allocate memory for HeadData in case we're not an Avatar instance if (!_headData) { _headData = new HeadData(this); + if (_forceFaceshiftConnected) { + _headData->_isFaceshiftConnected = true; + } } QByteArray avatarDataByteArray; diff --git a/libraries/avatars/src/AvatarData.h b/libraries/avatars/src/AvatarData.h index 1b8f6e6007..768633c366 100755 --- a/libraries/avatars/src/AvatarData.h +++ b/libraries/avatars/src/AvatarData.h @@ -206,6 +206,10 @@ public: Q_INVOKABLE virtual QStringList getJointNames() const { return _jointNames; } + Q_INVOKABLE void setBlendshape(QString name, float val) { _headData->setBlendshape(name, val); } + + void setForceFaceshiftConnected(bool connected) { _forceFaceshiftConnected = connected; } + // key state void setKeyState(KeyState s) { _keyState = s; } KeyState keyState() const { return _keyState; } @@ -300,7 +304,7 @@ protected: std::string _chatMessage; bool _isChatCirclingEnabled; - + bool _forceFaceshiftConnected; bool _hasNewJointRotations; // set in AvatarData, cleared in Avatar HeadData* _headData; diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index c691a2c28a..31001bf162 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -16,6 +16,8 @@ #include "AvatarData.h" #include "HeadData.h" +#include "../fbx/src/FBXReader.h" + HeadData::HeadData(AvatarData* owningAvatar) : _baseYaw(0.0f), _basePitch(0.0f), @@ -52,6 +54,26 @@ void HeadData::setOrientation(const glm::quat& orientation) { _baseRoll = eulers.z; } +void HeadData::setBlendshape(QString name, float val) { + static bool hasInitializedLookupMap = false; + static QMap blendshapeLookupMap; + //Lazily construct a lookup map from the blendshapes + if (!hasInitializedLookupMap) { + for (int i = 0; i < NUM_FACESHIFT_BLENDSHAPES; i++) { + blendshapeLookupMap[FACESHIFT_BLENDSHAPES[i]] = i; + } + } + + //Check to see if the named blendshape exists, and then set its value if it does + auto it = blendshapeLookupMap.find(name); + if (it != blendshapeLookupMap.end()) { + if (_blendshapeCoefficients.size() <= it.value()) { + _blendshapeCoefficients.resize(it.value() + 1); + } + _blendshapeCoefficients[it.value()] = val; + } +} + void HeadData::addYaw(float yaw) { setBaseYaw(_baseYaw + yaw); } diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index 9e2920ae85..782386c649 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -54,6 +54,7 @@ public: float getAudioAverageLoudness() const { return _audioAverageLoudness; } void setAudioAverageLoudness(float audioAverageLoudness) { _audioAverageLoudness = audioAverageLoudness; } + void setBlendshape(QString name, float val); const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } float getPupilDilation() const { return _pupilDilation; } diff --git a/libraries/fbx/src/FBXReader.cpp b/libraries/fbx/src/FBXReader.cpp index f366b6a5c3..cf726800a1 100644 --- a/libraries/fbx/src/FBXReader.cpp +++ b/libraries/fbx/src/FBXReader.cpp @@ -577,6 +577,8 @@ const char* FACESHIFT_BLENDSHAPES[] = { "" }; +const int NUM_FACESHIFT_BLENDSHAPES = sizeof(FACESHIFT_BLENDSHAPES) / sizeof(char*); + const char* HUMANIK_JOINTS[] = { "RightHand", "RightForeArm", diff --git a/libraries/fbx/src/FBXReader.h b/libraries/fbx/src/FBXReader.h index c336252574..b5340978c1 100644 --- a/libraries/fbx/src/FBXReader.h +++ b/libraries/fbx/src/FBXReader.h @@ -29,6 +29,8 @@ typedef QList FBXNodeList; /// The names of the blendshapes expected by Faceshift, terminated with an empty string. extern const char* FACESHIFT_BLENDSHAPES[]; +/// The size of FACESHIFT_BLENDSHAPES +extern const int NUM_FACESHIFT_BLENDSHAPES; /// The names of the joints in the Maya HumanIK rig, terminated with an empty string. extern const char* HUMANIK_JOINTS[]; From 3d3b4572e30a756c61fa97f3f9b7ad7127919635 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Wed, 23 Jul 2014 17:19:41 -0700 Subject: [PATCH 12/14] Added bot_randomExpression.js to test blendshapes --- examples/bot_randomExpression.js | 144 +++++++++++++++++++++++++++++++ 1 file changed, 144 insertions(+) create mode 100644 examples/bot_randomExpression.js diff --git a/examples/bot_randomExpression.js b/examples/bot_randomExpression.js new file mode 100644 index 0000000000..2d2653e6d5 --- /dev/null +++ b/examples/bot_randomExpression.js @@ -0,0 +1,144 @@ +// +// bot_randomExpression.js +// examples +// +// Created by Ben Arnold on 7/23/14. +// Copyright 2014 High Fidelity, Inc. +// +// This is an example script that demonstrates an NPC avatar with +// random facial expressions. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +function getRandomFloat(min, max) { + return Math.random() * (max - min) + min; +} + +function getRandomInt (min, max) { + return Math.floor(Math.random() * (max - min + 1)) + min; +} + +function printVector(string, vector) { + print(string + " " + vector.x + ", " + vector.y + ", " + vector.z); +} + +var timePassed = 0.0; +var updateSpeed = 3.0; + +var X_MIN = 5.0; +var X_MAX = 15.0; +var Z_MIN = 5.0; +var Z_MAX = 15.0; +var Y_PELVIS = 1.0; + +// pick an integer between 1 and 100 for the body model for this bot +botNumber = getRandomInt(1, 100); + +newFaceFilePrefix = "ron"; + +newBodyFilePrefix = "bot" + botNumber; + +// set the face model fst using the bot number +// there is no need to change the body model - we're using the default +Avatar.faceModelURL = "https://s3-us-west-1.amazonaws.com/highfidelity-public/meshes/" + newFaceFilePrefix + ".fst"; +Avatar.skeletonModelURL = "https://s3-us-west-1.amazonaws.com/highfidelity-public/meshes/" + newBodyFilePrefix + ".fst"; +Avatar.billboardURL = "https://s3-us-west-1.amazonaws.com/highfidelity-public/meshes/billboards/bot" + botNumber + ".png"; + +Agent.isAvatar = true; +Agent.isListeningToAudioStream = true; + +// change the avatar's position to the random one +Avatar.position = { x: getRandomFloat(X_MIN, X_MAX), y: Y_PELVIS, z: getRandomFloat(Z_MIN, Z_MAX) };; +printVector("New bot, position = ", Avatar.position); + +var allBlendShapes = []; +var targetBlendCoefficient = []; +var currentBlendCoefficient = []; + +function addBlendShape(s) { + allBlendShapes[allBlendShapes.length] = s; +} + +//It is imperative that the following blendshapes are all present and are in the correct order +addBlendShape("EyeBlink_L"); +addBlendShape("EyeBlink_R"); +addBlendShape("EyeSquint_L"); +addBlendShape("EyeSquint_R"); +addBlendShape("EyeDown_L"); +addBlendShape("EyeDown_R"); +addBlendShape("EyeIn_L"); +addBlendShape("EyeIn_R"); +addBlendShape("EyeOpen_L"); +addBlendShape("EyeOpen_R"); +addBlendShape("EyeOut_L"); +addBlendShape("EyeOut_R"); +addBlendShape("EyeUp_L"); +addBlendShape("EyeUp_R"); +addBlendShape("BrowsD_L"); +addBlendShape("BrowsD_R"); +addBlendShape("BrowsU_C"); +addBlendShape("BrowsU_L"); +addBlendShape("BrowsU_R"); +addBlendShape("JawFwd"); +addBlendShape("JawLeft"); +addBlendShape("JawOpen"); +addBlendShape("JawChew"); +addBlendShape("JawRight"); +addBlendShape("MouthLeft"); +addBlendShape("MouthRight"); +addBlendShape("MouthFrown_L"); +addBlendShape("MouthFrown_R"); +addBlendShape("MouthSmile_L"); +addBlendShape("MouthSmile_R"); +addBlendShape("MouthDimple_L"); +addBlendShape("MouthDimple_R"); +addBlendShape("LipsStretch_L"); +addBlendShape("LipsStretch_R"); +addBlendShape("LipsUpperClose"); +addBlendShape("LipsLowerClose"); +addBlendShape("LipsUpperUp"); +addBlendShape("LipsLowerDown"); +addBlendShape("LipsUpperOpen"); +addBlendShape("LipsLowerOpen"); +addBlendShape("LipsFunnel"); +addBlendShape("LipsPucker"); +addBlendShape("ChinLowerRaise"); +addBlendShape("ChinUpperRaise"); +addBlendShape("Sneer"); +addBlendShape("Puff"); +addBlendShape("CheekSquint_L"); +addBlendShape("CheekSquint_R"); + +for (var i = 0; i < allBlendShapes.length; i++) { + targetBlendCoefficient[i] = 0; + currentBlendCoefficient[i] = 0; +} + +function setRandomExpression() { + for (var i = 0; i < allBlendShapes.length; i++) { + targetBlendCoefficient[i] = Math.random(); + } +} + +var expressionChangeSpeed = 0.1; + +function updateBlendShapes(deltaTime) { + + for (var i = 0; i < allBlendShapes.length; i++) { + currentBlendCoefficient[i] += (targetBlendCoefficient[i] - currentBlendCoefficient[i]) * expressionChangeSpeed; + Avatar.setBlendshape(allBlendShapes[i], currentBlendCoefficient[i]); + } +} + +function update(deltaTime) { + timePassed += deltaTime; + if (timePassed > updateSpeed) { + timePassed = 0; + setRandomExpression(); + } + updateBlendShapes(deltaTime); +} + +Script.update.connect(update); \ No newline at end of file From 9ac8b732f09d377b9b26e6811b55fb0a45db6b0e Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Thu, 24 Jul 2014 10:32:34 -0700 Subject: [PATCH 13/14] FIxed error on ubuntu --- libraries/avatars/src/HeadData.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index 31001bf162..b29277ddeb 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -65,7 +65,7 @@ void HeadData::setBlendshape(QString name, float val) { } //Check to see if the named blendshape exists, and then set its value if it does - auto it = blendshapeLookupMap.find(name); + QMap::iterator it = blendshapeLookupMap.find(name); if (it != blendshapeLookupMap.end()) { if (_blendshapeCoefficients.size() <= it.value()) { _blendshapeCoefficients.resize(it.value() + 1); From ce1b8cdafc3e313b4f73629ab80399d51d96c9b0 Mon Sep 17 00:00:00 2001 From: barnold1953 Date: Thu, 24 Jul 2014 17:32:41 -0700 Subject: [PATCH 14/14] Multicursor editvoxels support --- examples/editVoxels.js | 121 +++++++++++++++++++++++------------------ 1 file changed, 69 insertions(+), 52 deletions(-) diff --git a/examples/editVoxels.js b/examples/editVoxels.js index 8d2a516f55..306156cc18 100644 --- a/examples/editVoxels.js +++ b/examples/editVoxels.js @@ -51,7 +51,6 @@ var lastVoxelScale = 0; var dragStart = { x: 0, y: 0 }; var wheelPixelsMoved = 0; - var mouseX = 0; var mouseY = 0; @@ -168,7 +167,16 @@ var voxelPreview = Overlays.addOverlay("cube", { lineWidth: 4 }); -var linePreviewTop = Overlays.addOverlay("line3d", { +var linePreviewTop = []; +var linePreviewBottom = []; +var linePreviewLeft = []; +var linePreviewRight = []; + +// Currend cursor index +var currentCursor = 0; + +function addLineOverlay() { + return Overlays.addOverlay("line3d", { position: { x: 0, y: 0, z: 0}, end: { x: 0, y: 0, z: 0}, color: { red: 255, green: 255, blue: 255}, @@ -176,34 +184,24 @@ var linePreviewTop = Overlays.addOverlay("line3d", { visible: false, lineWidth: previewLineWidth }); +} + +//Cursor line previews for up to three cursors +linePreviewTop[0] = addLineOverlay(); +linePreviewTop[1] = addLineOverlay(); +linePreviewTop[2] = addLineOverlay(); -var linePreviewBottom = Overlays.addOverlay("line3d", { - position: { x: 0, y: 0, z: 0}, - end: { x: 0, y: 0, z: 0}, - color: { red: 255, green: 255, blue: 255}, - alpha: 1, - visible: false, - lineWidth: previewLineWidth - }); - -var linePreviewLeft = Overlays.addOverlay("line3d", { - position: { x: 0, y: 0, z: 0}, - end: { x: 0, y: 0, z: 0}, - color: { red: 255, green: 255, blue: 255}, - alpha: 1, - visible: false, - lineWidth: previewLineWidth - }); - -var linePreviewRight = Overlays.addOverlay("line3d", { - position: { x: 0, y: 0, z: 0}, - end: { x: 0, y: 0, z: 0}, - color: { red: 255, green: 255, blue: 255}, - alpha: 1, - visible: false, - lineWidth: previewLineWidth - }); - +linePreviewBottom[0] = addLineOverlay(); +linePreviewBottom[1] = addLineOverlay(); +linePreviewBottom[2] = addLineOverlay(); + +linePreviewLeft[0] = addLineOverlay(); +linePreviewLeft[1] = addLineOverlay(); +linePreviewLeft[2] = addLineOverlay(); + +linePreviewRight[0] = addLineOverlay(); +linePreviewRight[1] = addLineOverlay(); +linePreviewRight[2] = addLineOverlay(); // these will be used below var scaleSelectorWidth = 144; @@ -809,21 +807,21 @@ function showPreviewLines() { var pasteVoxel = getNewPasteVoxel(pickRay); // X axis - Overlays.editOverlay(linePreviewBottom, { + Overlays.editOverlay(linePreviewBottom[currentCursor], { position: pasteVoxel.origin, end: {x: pasteVoxel.origin.x + pasteVoxel.voxelSize, y: pasteVoxel.origin.y, z: pasteVoxel.origin.z }, visible: true }); // Y axis - Overlays.editOverlay(linePreviewRight, { + Overlays.editOverlay(linePreviewRight[currentCursor], { position: pasteVoxel.origin, end: {x: pasteVoxel.origin.x, y: pasteVoxel.origin.y + pasteVoxel.voxelSize, z: pasteVoxel.origin.z }, visible: true }); // Z axis - Overlays.editOverlay(linePreviewTop, { + Overlays.editOverlay(linePreviewTop[currentCursor], { position: pasteVoxel.origin, end: {x: pasteVoxel.origin.x, y: pasteVoxel.origin.y, z: pasteVoxel.origin.z - pasteVoxel.voxelSize }, visible: true @@ -837,10 +835,10 @@ function showPreviewLines() { if (intersection.intersects) { resultVoxel = calculateVoxelFromIntersection(intersection,""); Overlays.editOverlay(voxelPreview, { visible: false }); - Overlays.editOverlay(linePreviewTop, { position: resultVoxel.topLeft, end: resultVoxel.topRight, visible: true }); - Overlays.editOverlay(linePreviewBottom, { position: resultVoxel.bottomLeft, end: resultVoxel.bottomRight, visible: true }); - Overlays.editOverlay(linePreviewLeft, { position: resultVoxel.topLeft, end: resultVoxel.bottomLeft, visible: true }); - Overlays.editOverlay(linePreviewRight, { position: resultVoxel.topRight, end: resultVoxel.bottomRight, visible: true }); + Overlays.editOverlay(linePreviewTop[currentCursor], { position: resultVoxel.topLeft, end: resultVoxel.topRight, visible: true }); + Overlays.editOverlay(linePreviewBottom[currentCursor], { position: resultVoxel.bottomLeft, end: resultVoxel.bottomRight, visible: true }); + Overlays.editOverlay(linePreviewLeft[currentCursor], { position: resultVoxel.topLeft, end: resultVoxel.bottomLeft, visible: true }); + Overlays.editOverlay(linePreviewRight[currentCursor], { position: resultVoxel.topRight, end: resultVoxel.bottomRight, visible: true }); colors[0] = {red: intersection.voxel.red, green: intersection.voxel.green , blue: intersection.voxel.blue }; if (copyScale) { @@ -849,10 +847,10 @@ function showPreviewLines() { moveTools(); } else { Overlays.editOverlay(voxelPreview, { visible: false }); - Overlays.editOverlay(linePreviewTop, { visible: false }); - Overlays.editOverlay(linePreviewBottom, { visible: false }); - Overlays.editOverlay(linePreviewLeft, { visible: false }); - Overlays.editOverlay(linePreviewRight, { visible: false }); + Overlays.editOverlay(linePreviewTop[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewBottom[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewLeft[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewRight[currentCursor], { visible: false }); } } @@ -862,20 +860,20 @@ function showPreviewGuides() { showPreviewVoxel(); // make sure alternative is hidden - Overlays.editOverlay(linePreviewTop, { visible: false }); - Overlays.editOverlay(linePreviewBottom, { visible: false }); - Overlays.editOverlay(linePreviewLeft, { visible: false }); - Overlays.editOverlay(linePreviewRight, { visible: false }); + Overlays.editOverlay(linePreviewTop[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewBottom[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewLeft[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewRight[currentCursor], { visible: false }); } else { showPreviewLines(); } } else { // make sure all previews are off Overlays.editOverlay(voxelPreview, { visible: false }); - Overlays.editOverlay(linePreviewTop, { visible: false }); - Overlays.editOverlay(linePreviewBottom, { visible: false }); - Overlays.editOverlay(linePreviewLeft, { visible: false }); - Overlays.editOverlay(linePreviewRight, { visible: false }); + Overlays.editOverlay(linePreviewTop[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewBottom[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewLeft[currentCursor], { visible: false }); + Overlays.editOverlay(linePreviewRight[currentCursor], { visible: false }); } } @@ -968,6 +966,14 @@ function mousePressEvent(event) { return; } + if (event.deviceID == 1500) { // Left Hydra Controller + currentCursor = 0; + } else if (event.deviceID == 1501) { // Right Hydra Controller + currentCursor = 1; + } else { + currentCursor = 2; + } + var clickedOnSomething = false; var clickedOverlay = Overlays.getOverlayAtPoint({x: event.x, y: event.y}); @@ -1220,6 +1226,7 @@ function menuItemEvent(menuItem) { } function mouseMoveEvent(event) { + if (!editToolsOn) { return; } @@ -1227,6 +1234,14 @@ function mouseMoveEvent(event) { return; } + if (event.deviceID == 1500) { // Left Hydra Controller + currentCursor = 0; + } else if (event.deviceID == 1501) { // Right Hydra Controller + currentCursor = 1; + } else { + currentCursor = 2; + } + // Move Import Preview if (isImporting) { var pickRay = Camera.computePickRay(event.x, event.y); @@ -1475,10 +1490,12 @@ Controller.captureKeyEvents({ text: "-" }); function scriptEnding() { Overlays.deleteOverlay(voxelPreview); - Overlays.deleteOverlay(linePreviewTop); - Overlays.deleteOverlay(linePreviewBottom); - Overlays.deleteOverlay(linePreviewLeft); - Overlays.deleteOverlay(linePreviewRight); + for (var i = 0; i < linePreviewTop.length; i++) { + Overlays.deleteOverlay(linePreviewTop[i]); + Overlays.deleteOverlay(linePreviewBottom[i]); + Overlays.deleteOverlay(linePreviewLeft[i]); + Overlays.deleteOverlay(linePreviewRight[i]); + } for (s = 0; s < numColors; s++) { Overlays.deleteOverlay(swatches[s]); }