mirror of
https://github.com/HifiExperiments/overte.git
synced 2025-04-07 10:02:24 +02:00
Merge branch 'master' of https://github.com/worklist/hifi into kinected
Conflicts: interface/src/Avatar.cpp
This commit is contained in:
commit
e866c22518
16 changed files with 230 additions and 109 deletions
|
@ -138,7 +138,7 @@ int main(int argc, const char* argv[]) {
|
|||
const char MIXER_LOGSTASH_METRIC_NAME[] = "audio-mixer-frame-time-usage";
|
||||
|
||||
float averageFrameTimePercentage = sumFrameTimePercentages / numStatCollections;
|
||||
Logstash::stashValue(STAT_TYPE_GAUGE, MIXER_LOGSTASH_METRIC_NAME, averageFrameTimePercentage);
|
||||
Logstash::stashValue(STAT_TYPE_TIMER, MIXER_LOGSTASH_METRIC_NAME, averageFrameTimePercentage);
|
||||
|
||||
sumFrameTimePercentages = 0.0f;
|
||||
numStatCollections = 0;
|
||||
|
|
|
@ -32,9 +32,9 @@ else (LEAP_LIBRARIES AND LEAP_INCLUDE_DIRS)
|
|||
endif ()
|
||||
|
||||
# If we're using the Leap stubs, there's only a header, no lib.
|
||||
if (LEAP_INCLUDE_DIRS)
|
||||
if (LEAP_LIBRARIES AND LEAP_INCLUDE_DIRS)
|
||||
set(LEAP_FOUND TRUE)
|
||||
endif (LEAP_INCLUDE_DIRS)
|
||||
endif (LEAP_LIBRARIES AND LEAP_INCLUDE_DIRS)
|
||||
|
||||
if (LEAP_FOUND)
|
||||
if (NOT Leap_FIND_QUIETLY)
|
||||
|
|
|
@ -181,7 +181,7 @@ int main(int argc, const char * argv[])
|
|||
// time to send our count of agents and servers to logstash
|
||||
const char NODE_COUNT_LOGSTASH_KEY[] = "ds-node-count";
|
||||
|
||||
Logstash::stashValue(STAT_TYPE_GAUGE, NODE_COUNT_LOGSTASH_KEY, agentList->getNumAliveAgents());
|
||||
Logstash::stashValue(STAT_TYPE_TIMER, NODE_COUNT_LOGSTASH_KEY, agentList->getNumAliveAgents());
|
||||
|
||||
gettimeofday(&lastStatSendTime, NULL);
|
||||
}
|
||||
|
|
|
@ -120,6 +120,7 @@ include_directories(
|
|||
${OPENCV_INCLUDE_DIRS}
|
||||
)
|
||||
|
||||
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -isystem ${OPENCV_INCLUDE_DIRS}")
|
||||
target_link_libraries(
|
||||
${TARGET_NAME}
|
||||
${QT_LIBRARIES}
|
||||
|
@ -161,8 +162,12 @@ if (APPLE)
|
|||
${QuartzCore}
|
||||
${UVCCAMERACONTROL_LIBRARIES}
|
||||
${LIBOVR_LIBRARIES}
|
||||
${LEAP_LIBRARIES}
|
||||
)
|
||||
|
||||
if (LEAP_FOUND)
|
||||
target_link_libraries(${TARGET_NAME} ${LEAP_LIBRARIES})
|
||||
endif(LEAP_FOUND)
|
||||
|
||||
else (APPLE)
|
||||
find_package(OpenGL REQUIRED)
|
||||
find_package(GLUT REQUIRED)
|
||||
|
|
|
@ -432,6 +432,9 @@ void Application::paintGL() {
|
|||
void Application::resizeGL(int width, int height) {
|
||||
float aspectRatio = ((float)width/(float)height); // based on screen resize
|
||||
|
||||
// reset the camera FOV to our preference...
|
||||
_myCamera.setFieldOfView(_horizontalFieldOfView);
|
||||
|
||||
// get the lens details from the current camera
|
||||
Camera& camera = _viewFrustumFromOffset->isChecked() ? _viewFrustumOffsetCamera : _myCamera;
|
||||
float nearClip = camera.getNearClip();
|
||||
|
@ -953,6 +956,8 @@ void Application::terminate() {
|
|||
// Close serial port
|
||||
// close(serial_fd);
|
||||
|
||||
LeapManager::terminate();
|
||||
|
||||
if (_settingsAutosave->isChecked()) {
|
||||
saveSettings();
|
||||
_settings->sync();
|
||||
|
@ -1645,6 +1650,8 @@ void Application::init() {
|
|||
QMetaObject::invokeMethod(_fullScreenMode, "trigger", Qt::QueuedConnection);
|
||||
}
|
||||
|
||||
LeapManager::initialize();
|
||||
|
||||
gettimeofday(&_timerStart, NULL);
|
||||
gettimeofday(&_lastTimeIdle, NULL);
|
||||
|
||||
|
@ -1803,7 +1810,8 @@ void Application::update(float deltaTime) {
|
|||
|
||||
// Leap finger-sensing device
|
||||
LeapManager::nextFrame();
|
||||
_myAvatar.getHand().setLeapFingers(LeapManager::getFingerPositions());
|
||||
_myAvatar.getHand().setLeapFingers(LeapManager::getFingerTips(), LeapManager::getFingerRoots());
|
||||
_myAvatar.getHand().setLeapHands(LeapManager::getHandPositions(), LeapManager::getHandNormals());
|
||||
|
||||
// Read serial port interface devices
|
||||
if (_serialHeadSensor.isActive()) {
|
||||
|
|
|
@ -286,15 +286,17 @@ void Avatar::reset() {
|
|||
|
||||
// Update avatar state with sensor data
|
||||
void Avatar::updateFromGyrosAndOrWebcam() {
|
||||
const float AMPLIFY_PITCH = 1.f;
|
||||
const float AMPLIFY_YAW = 1.f;
|
||||
const float AMPLIFY_ROLL = 1.f;
|
||||
const float AMPLIFY_PITCH = 2.f;
|
||||
const float AMPLIFY_YAW = 2.f;
|
||||
const float AMPLIFY_ROLL = 2.f;
|
||||
|
||||
SerialInterface* gyros = Application::getInstance()->getSerialHeadSensor();
|
||||
Webcam* webcam = Application::getInstance()->getWebcam();
|
||||
glm::vec3 estimatedPosition, estimatedRotation;
|
||||
if (gyros->isActive()) {
|
||||
estimatedPosition = gyros->getEstimatedPosition();
|
||||
if (webcam->isActive()) {
|
||||
estimatedPosition = webcam->getEstimatedPosition();
|
||||
}
|
||||
estimatedRotation = gyros->getEstimatedRotation();
|
||||
|
||||
} else if (webcam->isActive()) {
|
||||
|
|
|
@ -107,6 +107,7 @@ public:
|
|||
|
||||
//getters
|
||||
bool isInitialized () const { return _initialized;}
|
||||
bool isMyAvatar () const { return _owningAgent == NULL; }
|
||||
const Skeleton& getSkeleton () const { return _skeleton;}
|
||||
float getHeadYawRate () const { return _head.yawRate;}
|
||||
float getBodyYaw () const { return _bodyYaw;}
|
||||
|
@ -155,13 +156,13 @@ public:
|
|||
void writeAvatarDataToFile();
|
||||
void readAvatarDataFromFile();
|
||||
|
||||
static void renderJointConnectingCone(glm::vec3 position1, glm::vec3 position2, float radius1, float radius2);
|
||||
|
||||
private:
|
||||
// privatize copy constructor and assignment operator to avoid copying
|
||||
Avatar(const Avatar&);
|
||||
Avatar& operator= (const Avatar&);
|
||||
|
||||
bool isMyAvatar() const { return _owningAgent == NULL; }
|
||||
|
||||
struct AvatarBall
|
||||
{
|
||||
AvatarJointID parentJoint; // the skeletal joint that serves as a reference for determining the position
|
||||
|
@ -237,7 +238,6 @@ private:
|
|||
void applyHardCollision(const glm::vec3& penetration, float elasticity, float damping);
|
||||
void applyCollisionWithOtherAvatar( Avatar * other, float deltaTime );
|
||||
void checkForMouseRayTouching();
|
||||
void renderJointConnectingCone(glm::vec3 position1, glm::vec3 position2, float radius1, float radius2);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -21,21 +21,19 @@ Hand::Hand(Avatar* owningAvatar) :
|
|||
_owningAvatar(owningAvatar),
|
||||
_renderAlpha(1.0),
|
||||
_lookingInMirror(false),
|
||||
_ballColor(0.0, 0.4, 0.0),
|
||||
_ballColor(0.0, 0.0, 0.4),
|
||||
_position(0.0, 0.4, 0.0),
|
||||
_orientation(0.0, 0.0, 0.0, 1.0)
|
||||
{
|
||||
}
|
||||
|
||||
void Hand::init() {
|
||||
_numLeapBalls = 0;
|
||||
for (int b = 0; b < MAX_AVATAR_LEAP_BALLS; b++) {
|
||||
_leapBall[b].position = glm::vec3(0.0, 0.0, 0.0);
|
||||
_leapBall[b].velocity = glm::vec3(0.0, 0.0, 0.0);
|
||||
_leapBall[b].radius = 0.01;
|
||||
_leapBall[b].touchForce = 0.0;
|
||||
_leapBall[b].isCollidable = true;
|
||||
// Different colors for my hand and others' hands
|
||||
if (_owningAvatar && _owningAvatar->isMyAvatar()) {
|
||||
_ballColor = glm::vec3(0.0, 0.4, 0.0);
|
||||
}
|
||||
else
|
||||
_ballColor = glm::vec3(0.0, 0.0, 0.4);
|
||||
}
|
||||
|
||||
void Hand::reset() {
|
||||
|
@ -44,20 +42,27 @@ void Hand::reset() {
|
|||
void Hand::simulate(float deltaTime, bool isMine) {
|
||||
}
|
||||
|
||||
glm::vec3 Hand::leapPositionToWorldPosition(const glm::vec3& leapPosition) {
|
||||
float unitScale = 0.001; // convert mm to meters
|
||||
return _position + _orientation * (leapPosition * unitScale);
|
||||
}
|
||||
|
||||
void Hand::calculateGeometry() {
|
||||
glm::vec3 offset(0.1, -0.1, -0.15); // place the hand in front of the face where we can see it
|
||||
glm::vec3 offset(0.2, -0.2, -0.3); // place the hand in front of the face where we can see it
|
||||
|
||||
Head& head = _owningAvatar->getHead();
|
||||
_position = head.getPosition() + head.getOrientation() * offset;
|
||||
_orientation = head.getOrientation();
|
||||
|
||||
_numLeapBalls = _fingerPositions.size();
|
||||
int numLeapBalls = _fingerTips.size() + _fingerRoots.size();
|
||||
_leapBalls.resize(numLeapBalls);
|
||||
|
||||
float unitScale = 0.001; // convert mm to meters
|
||||
for (int b = 0; b < _numLeapBalls; b++) {
|
||||
glm::vec3 pos = unitScale * _fingerPositions[b] + offset;
|
||||
_leapBall[b].rotation = _orientation;
|
||||
_leapBall[b].position = _position + _orientation * pos;
|
||||
for (int i = 0; i < _fingerTips.size(); ++i) {
|
||||
_leapBalls[i].rotation = _orientation;
|
||||
_leapBalls[i].position = leapPositionToWorldPosition(_fingerTips[i]);
|
||||
_leapBalls[i].radius = 0.01;
|
||||
_leapBalls[i].touchForce = 0.0;
|
||||
_leapBalls[i].isCollidable = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -78,23 +83,52 @@ void Hand::render(bool lookingInMirror) {
|
|||
void Hand::renderHandSpheres() {
|
||||
glPushMatrix();
|
||||
// Draw the leap balls
|
||||
for (int b = 0; b < _numLeapBalls; b++) {
|
||||
for (size_t i = 0; i < _leapBalls.size(); i++) {
|
||||
float alpha = 1.0f;
|
||||
|
||||
if (alpha > 0.0f) {
|
||||
glColor4f(_ballColor.r, _ballColor.g, _ballColor.b, alpha); // Just to test
|
||||
glColor4f(_ballColor.r, _ballColor.g, _ballColor.b, alpha);
|
||||
|
||||
glPushMatrix();
|
||||
glTranslatef(_leapBall[b].position.x, _leapBall[b].position.y, _leapBall[b].position.z);
|
||||
glutSolidSphere(_leapBall[b].radius, 20.0f, 20.0f);
|
||||
glTranslatef(_leapBalls[i].position.x, _leapBalls[i].position.y, _leapBalls[i].position.z);
|
||||
glutSolidSphere(_leapBalls[i].radius, 20.0f, 20.0f);
|
||||
glPopMatrix();
|
||||
}
|
||||
}
|
||||
|
||||
// Draw the finger root cones
|
||||
if (_fingerTips.size() == _fingerRoots.size()) {
|
||||
for (size_t i = 0; i < _fingerTips.size(); ++i) {
|
||||
glColor4f(_ballColor.r, _ballColor.g, _ballColor.b, 0.5);
|
||||
glm::vec3 tip = leapPositionToWorldPosition(_fingerTips[i]);
|
||||
glm::vec3 root = leapPositionToWorldPosition(_fingerRoots[i]);
|
||||
Avatar::renderJointConnectingCone(root, tip, 0.001, 0.003);
|
||||
}
|
||||
}
|
||||
|
||||
// Draw the palms
|
||||
if (_handPositions.size() == _handNormals.size()) {
|
||||
for (size_t i = 0; i < _handPositions.size(); ++i) {
|
||||
glColor4f(_ballColor.r, _ballColor.g, _ballColor.b, 0.25);
|
||||
glm::vec3 tip = leapPositionToWorldPosition(_handPositions[i]);
|
||||
glm::vec3 root = leapPositionToWorldPosition(_handPositions[i] + (_handNormals[i] * 2.0f));
|
||||
Avatar::renderJointConnectingCone(root, tip, 0.05, 0.03);
|
||||
}
|
||||
}
|
||||
|
||||
glPopMatrix();
|
||||
}
|
||||
|
||||
void Hand::setLeapFingers(const std::vector<glm::vec3>& fingerPositions) {
|
||||
_fingerPositions = fingerPositions;
|
||||
void Hand::setLeapFingers(const std::vector<glm::vec3>& fingerTips,
|
||||
const std::vector<glm::vec3>& fingerRoots) {
|
||||
_fingerTips = fingerTips;
|
||||
_fingerRoots = fingerRoots;
|
||||
}
|
||||
|
||||
void Hand::setLeapHands(const std::vector<glm::vec3>& handPositions,
|
||||
const std::vector<glm::vec3>& handNormals) {
|
||||
_handPositions = handPositions;
|
||||
_handNormals = handNormals;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include "InterfaceConfig.h"
|
||||
#include "SerialInterface.h"
|
||||
#include <SharedUtil.h>
|
||||
#include <vector>
|
||||
|
||||
|
||||
class Avatar;
|
||||
|
@ -41,11 +42,13 @@ public:
|
|||
void render(bool lookingInMirror);
|
||||
|
||||
void setBallColor (glm::vec3 ballColor ) { _ballColor = ballColor; }
|
||||
void setLeapFingers (const std::vector<glm::vec3>& fingerPositions);
|
||||
void setLeapFingers (const std::vector<glm::vec3>& fingerTips,
|
||||
const std::vector<glm::vec3>& fingerRoots);
|
||||
void setLeapHands (const std::vector<glm::vec3>& handPositions,
|
||||
const std::vector<glm::vec3>& handNormals);
|
||||
|
||||
// getters
|
||||
int getNumLeapBalls () const { return _numLeapBalls;}
|
||||
const glm::vec3& getLeapBallPosition (int which) const { return _leapBall[which].position;}
|
||||
const glm::vec3& getLeapBallPosition (int ball) const { return _leapBalls[ball].position;}
|
||||
|
||||
private:
|
||||
// disallow copies of the Hand, copy of owning Avatar is disallowed too
|
||||
|
@ -58,12 +61,12 @@ private:
|
|||
glm::vec3 _ballColor;
|
||||
glm::vec3 _position;
|
||||
glm::quat _orientation;
|
||||
int _numLeapBalls;
|
||||
HandBall _leapBall[ MAX_AVATAR_LEAP_BALLS ];
|
||||
std::vector<HandBall> _leapBalls;
|
||||
|
||||
// private methods
|
||||
void renderHandSpheres();
|
||||
void calculateGeometry();
|
||||
glm::vec3 leapPositionToWorldPosition(const glm::vec3& leapPosition);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -179,7 +179,7 @@ void Head::simulate(float deltaTime, bool isMine) {
|
|||
_browAudioLift *= 0.7f;
|
||||
|
||||
// update eyelid blinking
|
||||
const float BLINK_SPEED = 5.0f;
|
||||
const float BLINK_SPEED = 10.0f;
|
||||
const float FULLY_OPEN = 0.0f;
|
||||
const float FULLY_CLOSED = 1.0f;
|
||||
if (_leftEyeBlinkVelocity == 0.0f && _rightEyeBlinkVelocity == 0.0f) {
|
||||
|
|
|
@ -11,25 +11,43 @@
|
|||
#include <dlfcn.h> // needed for RTLD_LAZY
|
||||
#include <sstream>
|
||||
|
||||
bool LeapManager::_isInitialized = false;
|
||||
bool LeapManager::_libraryExists = false;
|
||||
Leap::Controller* LeapManager::_controller = 0;
|
||||
HifiLeapListener* LeapManager::_listener = 0;
|
||||
Leap::Controller* LeapManager::_controller = NULL;
|
||||
HifiLeapListener* LeapManager::_listener = NULL;
|
||||
|
||||
class HifiLeapListener : public Leap::Listener {
|
||||
public:
|
||||
Leap::Frame lastFrame;
|
||||
std::vector<glm::vec3> fingerPositions;
|
||||
std::vector<glm::vec3> fingerTips;
|
||||
std::vector<glm::vec3> fingerRoots;
|
||||
std::vector<glm::vec3> handPositions;
|
||||
std::vector<glm::vec3> handNormals;
|
||||
|
||||
virtual void onFrame(const Leap::Controller& controller) {
|
||||
#ifndef LEAP_STUBS
|
||||
Leap::Frame frame = controller.frame();
|
||||
int numFingers = frame.fingers().count();
|
||||
fingerPositions.resize(numFingers);
|
||||
fingerTips.resize(numFingers);
|
||||
fingerRoots.resize(numFingers);
|
||||
for (int i = 0; i < numFingers; ++i) {
|
||||
const Leap::Finger& thisFinger = frame.fingers()[i];
|
||||
const Leap::Vector pos = thisFinger.tipPosition();
|
||||
fingerPositions[i] = glm::vec3(pos.x, pos.y, pos.z);
|
||||
const Leap::Vector pos = thisFinger.stabilizedTipPosition();
|
||||
fingerTips[i] = glm::vec3(pos.x, pos.y, pos.z);
|
||||
|
||||
const Leap::Vector root = pos - thisFinger.direction() * thisFinger.length();
|
||||
fingerRoots[i] = glm::vec3(root.x, root.y, root.z);
|
||||
}
|
||||
|
||||
int numHands = frame.hands().count();
|
||||
handPositions.resize(numHands);
|
||||
handNormals.resize(numHands);
|
||||
for (int i = 0; i < numHands; ++i) {
|
||||
const Leap::Hand& thisHand = frame.hands()[i];
|
||||
const Leap::Vector pos = thisHand.palmPosition();
|
||||
handPositions[i] = glm::vec3(pos.x, pos.y, pos.z);
|
||||
|
||||
const Leap::Vector norm = thisHand.palmNormal();
|
||||
handNormals[i] = glm::vec3(norm.x, norm.y, norm.z);
|
||||
}
|
||||
lastFrame = frame;
|
||||
#endif
|
||||
|
@ -38,28 +56,61 @@ public:
|
|||
};
|
||||
|
||||
void LeapManager::initialize() {
|
||||
if (!_isInitialized) {
|
||||
#ifndef LEAP_STUBS
|
||||
if (dlopen("/usr/lib/libLeap.dylib", RTLD_LAZY)) {
|
||||
_libraryExists = true;
|
||||
_controller = new Leap::Controller();
|
||||
_listener = new HifiLeapListener();
|
||||
_controller->addListener(*_listener);
|
||||
}
|
||||
#endif
|
||||
_isInitialized = true;
|
||||
if (dlopen("/usr/lib/libLeap.dylib", RTLD_LAZY)) {
|
||||
_libraryExists = true;
|
||||
_controller = new Leap::Controller();
|
||||
_listener = new HifiLeapListener();
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void LeapManager::terminate() {
|
||||
delete _listener;
|
||||
delete _controller;
|
||||
_listener = NULL;
|
||||
_controller = NULL;
|
||||
}
|
||||
|
||||
void LeapManager::nextFrame() {
|
||||
initialize();
|
||||
if (_listener && _controller)
|
||||
_listener->onFrame(*_controller);
|
||||
}
|
||||
|
||||
const std::vector<glm::vec3>& LeapManager::getFingerPositions() {
|
||||
if (_listener)
|
||||
return _listener->fingerPositions;
|
||||
const std::vector<glm::vec3>& LeapManager::getFingerTips() {
|
||||
if (_listener) {
|
||||
return _listener->fingerTips;
|
||||
}
|
||||
else {
|
||||
static std::vector<glm::vec3> empty;
|
||||
return empty;
|
||||
}
|
||||
}
|
||||
|
||||
const std::vector<glm::vec3>& LeapManager::getFingerRoots() {
|
||||
if (_listener) {
|
||||
return _listener->fingerRoots;
|
||||
}
|
||||
else {
|
||||
static std::vector<glm::vec3> empty;
|
||||
return empty;
|
||||
}
|
||||
}
|
||||
|
||||
const std::vector<glm::vec3>& LeapManager::getHandPositions() {
|
||||
if (_listener) {
|
||||
return _listener->handPositions;
|
||||
}
|
||||
else {
|
||||
static std::vector<glm::vec3> empty;
|
||||
return empty;
|
||||
}
|
||||
}
|
||||
|
||||
const std::vector<glm::vec3>& LeapManager::getHandNormals() {
|
||||
if (_listener) {
|
||||
return _listener->handNormals;
|
||||
}
|
||||
else {
|
||||
static std::vector<glm::vec3> empty;
|
||||
return empty;
|
||||
|
@ -69,17 +120,15 @@ const std::vector<glm::vec3>& LeapManager::getFingerPositions() {
|
|||
std::string LeapManager::statusString() {
|
||||
std::stringstream leapString;
|
||||
#ifndef LEAP_STUBS
|
||||
if (_isInitialized) {
|
||||
if (!_libraryExists)
|
||||
leapString << "Leap library at /usr/lib/libLeap.dylib does not exist.";
|
||||
else if (!_controller || !_listener || !_controller->devices().count())
|
||||
leapString << "Leap controller is not attached.";
|
||||
else {
|
||||
leapString << "Leap pointables: " << _listener->lastFrame.pointables().count();
|
||||
if (_listener->lastFrame.pointables().count() > 0) {
|
||||
Leap::Vector pos = _listener->lastFrame.pointables()[0].tipPosition();
|
||||
leapString << " pos: " << pos.x << " " << pos.y << " " << pos.z;
|
||||
}
|
||||
if (!_libraryExists)
|
||||
leapString << "Leap library at /usr/lib/libLeap.dylib does not exist.";
|
||||
else if (!_controller || !_listener || !_controller->devices().count())
|
||||
leapString << "Leap controller is not attached.";
|
||||
else {
|
||||
leapString << "Leap pointables: " << _listener->lastFrame.pointables().count();
|
||||
if (_listener->lastFrame.pointables().count() > 0) {
|
||||
Leap::Vector pos = _listener->lastFrame.pointables()[0].tipPosition();
|
||||
leapString << " pos: " << pos.x << " " << pos.y << " " << pos.z;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -21,19 +21,18 @@ namespace Leap {
|
|||
class LeapManager {
|
||||
public:
|
||||
static void nextFrame(); // called once per frame to get new Leap data
|
||||
static const std::vector<glm::vec3>& getFingerPositions();
|
||||
static const std::vector<glm::vec3>& getFingerTips();
|
||||
static const std::vector<glm::vec3>& getFingerRoots();
|
||||
static const std::vector<glm::vec3>& getHandPositions();
|
||||
static const std::vector<glm::vec3>& getHandNormals();
|
||||
static std::string statusString();
|
||||
static void initialize();
|
||||
static void terminate();
|
||||
|
||||
private:
|
||||
static void initialize();
|
||||
static bool _isInitialized; // We've looked for the library and hooked it up if it's there.
|
||||
static bool _libraryExists; // The library is present, so we won't crash if we call it.
|
||||
static Leap::Controller* _controller;
|
||||
static HifiLeapListener* _listener;
|
||||
|
||||
|
||||
|
||||
|
||||
};
|
||||
|
||||
#endif /* defined(__hifi__LeapManager__) */
|
||||
|
|
|
@ -341,12 +341,6 @@ void SerialInterface::readData(float deltaTime) {
|
|||
|
||||
_estimatedRotation = safeEulerAngles(estimatedRotation);
|
||||
|
||||
// Fuse gyro roll with webcam roll
|
||||
if (webcam->isActive()) {
|
||||
_estimatedRotation.z = glm::mix(_estimatedRotation.z, webcam->getEstimatedRotation().z,
|
||||
1.0f / SENSOR_FUSION_SAMPLES);
|
||||
}
|
||||
|
||||
totalSamples++;
|
||||
}
|
||||
|
||||
|
|
|
@ -125,13 +125,31 @@ int AvatarData::getBroadcastData(unsigned char* destinationBuffer) {
|
|||
*destinationBuffer++ = bitItems;
|
||||
|
||||
// leap hand data
|
||||
const std::vector<glm::vec3>& fingerPositions = _handData->getFingerPositions();
|
||||
*destinationBuffer++ = (unsigned char)fingerPositions.size();
|
||||
for (size_t i = 0; i < fingerPositions.size(); ++i)
|
||||
{
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerPositions[i].x, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerPositions[i].y, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerPositions[i].z, 4);
|
||||
// In order to make the hand data version-robust, hand data packing is just a series of vec3's,
|
||||
// with conventions. If a client doesn't know the conventions, they can just get the vec3's
|
||||
// and render them as balls, or ignore them, without crashing or disrupting anyone.
|
||||
// Current convention:
|
||||
// Zero or more fingetTip positions, followed by the same number of fingerRoot positions
|
||||
|
||||
const std::vector<glm::vec3>& fingerTips = _handData->getFingerTips();
|
||||
const std::vector<glm::vec3>& fingerRoots = _handData->getFingerRoots();
|
||||
size_t numFingerVectors = fingerTips.size() + fingerRoots.size();
|
||||
if (numFingerVectors > 255)
|
||||
numFingerVectors = 0; // safety. We shouldn't ever get over 255, so consider that invalid.
|
||||
|
||||
*destinationBuffer++ = (unsigned char)numFingerVectors;
|
||||
|
||||
if (numFingerVectors > 0) {
|
||||
for (size_t i = 0; i < fingerTips.size(); ++i) {
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerTips[i].x, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerTips[i].y, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerTips[i].z, 4);
|
||||
}
|
||||
for (size_t i = 0; i < fingerRoots.size(); ++i) {
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerRoots[i].x, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerRoots[i].y, 4);
|
||||
destinationBuffer += packFloatScalarToSignedTwoByteFixed(destinationBuffer, fingerRoots[i].z, 4);
|
||||
}
|
||||
}
|
||||
|
||||
return destinationBuffer - bufferStart;
|
||||
|
@ -229,18 +247,20 @@ int AvatarData::parseData(unsigned char* sourceBuffer, int numBytes) {
|
|||
// leap hand data
|
||||
if (sourceBuffer - startPosition < numBytes) // safety check
|
||||
{
|
||||
std::vector<glm::vec3> fingerPositions = _handData->getFingerPositions();
|
||||
unsigned int numFingers = *sourceBuffer++;
|
||||
if (numFingers > MAX_AVATAR_LEAP_BALLS) // safety check
|
||||
numFingers = 0;
|
||||
fingerPositions.resize(numFingers);
|
||||
for (size_t i = 0; i < numFingers; ++i)
|
||||
{
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerPositions[i].x), 4);
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerPositions[i].y), 4);
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerPositions[i].z), 4);
|
||||
std::vector<glm::vec3> fingerTips = _handData->getFingerTips();
|
||||
std::vector<glm::vec3> fingerRoots = _handData->getFingerRoots();
|
||||
unsigned int numFingerVectors = *sourceBuffer++;
|
||||
unsigned int numFingerTips = numFingerVectors / 2;
|
||||
unsigned int numFingerRoots = numFingerVectors - numFingerTips;
|
||||
fingerTips.resize(numFingerTips);
|
||||
fingerRoots.resize(numFingerRoots);
|
||||
for (size_t i = 0; i < numFingerTips; ++i) {
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerTips[i].x), 4);
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerTips[i].y), 4);
|
||||
sourceBuffer += unpackFloatScalarFromSignedTwoByteFixed((int16_t*) sourceBuffer, &(fingerTips[i].z), 4);
|
||||
}
|
||||
_handData->setFingerPositions(fingerPositions);
|
||||
_handData->setFingerTips(fingerTips);
|
||||
_handData->setFingerRoots(fingerRoots);
|
||||
}
|
||||
|
||||
return sourceBuffer - startPosition;
|
||||
|
|
|
@ -14,20 +14,27 @@
|
|||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
#define MAX_AVATAR_LEAP_BALLS 10
|
||||
|
||||
class AvatarData;
|
||||
|
||||
class HandData {
|
||||
public:
|
||||
HandData(AvatarData* owningAvatar);
|
||||
|
||||
const std::vector<glm::vec3>& getFingerPositions() const { return _fingerPositions; }
|
||||
void setFingerPositions(const std::vector<glm::vec3>& fingerPositions) { _fingerPositions = fingerPositions; }
|
||||
const std::vector<glm::vec3>& getFingerTips() const { return _fingerTips; }
|
||||
const std::vector<glm::vec3>& getFingerRoots() const { return _fingerRoots; }
|
||||
const std::vector<glm::vec3>& getHandPositions() const { return _handPositions; }
|
||||
const std::vector<glm::vec3>& getHandNormals() const { return _handNormals; }
|
||||
void setFingerTips(const std::vector<glm::vec3>& fingerTips) { _fingerTips = fingerTips; }
|
||||
void setFingerRoots(const std::vector<glm::vec3>& fingerRoots) { _fingerRoots = fingerRoots; }
|
||||
void setHandPositions(const std::vector<glm::vec3>& handPositons) { _handPositions = handPositons; }
|
||||
void setHandNormals(const std::vector<glm::vec3>& handNormals) { _handNormals = handNormals; }
|
||||
|
||||
friend class AvatarData;
|
||||
protected:
|
||||
std::vector<glm::vec3> _fingerPositions;
|
||||
std::vector<glm::vec3> _fingerTips;
|
||||
std::vector<glm::vec3> _fingerRoots;
|
||||
std::vector<glm::vec3> _handPositions;
|
||||
std::vector<glm::vec3> _handNormals;
|
||||
AvatarData* _owningAvatarData;
|
||||
private:
|
||||
// privatize copy ctor and assignment operator so copies of this object cannot be made
|
||||
|
|
|
@ -45,12 +45,12 @@ bool Logstash::shouldSendStats() {
|
|||
return shouldSendStats;
|
||||
}
|
||||
|
||||
void Logstash::stashValue(char valueType, const char* key, float value) {
|
||||
void Logstash::stashValue(char statType, const char* key, float value) {
|
||||
static char logstashPacket[MAX_PACKET_SIZE];
|
||||
|
||||
// load up the logstash packet with the key and the passed float value
|
||||
// send it to 4 decimal places
|
||||
int numPacketBytes = sprintf(logstashPacket, "%c %s %.4f", valueType, key, value);
|
||||
int numPacketBytes = sprintf(logstashPacket, "%c %s %.4f", statType, key, value);
|
||||
|
||||
AgentList *agentList = AgentList::getInstance();
|
||||
|
||||
|
|
Loading…
Reference in a new issue