mirror of
https://github.com/overte-org/overte.git
synced 2025-04-22 16:13:28 +02:00
Merge pull request #4071 from Atlante45/head_rotation_fix
Head rotation fix
This commit is contained in:
commit
22a609f014
5 changed files with 26 additions and 95 deletions
|
@ -454,47 +454,6 @@ void Avatar::render(const glm::vec3& cameraPosition, RenderMode renderMode, bool
|
|||
return;
|
||||
}
|
||||
renderDisplayName();
|
||||
|
||||
if (!_chatMessage.empty()) {
|
||||
int width = 0;
|
||||
int lastWidth = 0;
|
||||
for (string::iterator it = _chatMessage.begin(); it != _chatMessage.end(); it++) {
|
||||
width += (lastWidth = textRenderer(CHAT)->computeWidth(*it));
|
||||
}
|
||||
glPushMatrix();
|
||||
|
||||
glm::vec3 chatPosition = getHead()->getEyePosition() + getBodyUpDirection() * CHAT_MESSAGE_HEIGHT * _scale;
|
||||
glTranslatef(chatPosition.x, chatPosition.y, chatPosition.z);
|
||||
glm::quat chatRotation = Application::getInstance()->getCamera()->getRotation();
|
||||
glm::vec3 chatAxis = glm::axis(chatRotation);
|
||||
glRotatef(glm::degrees(glm::angle(chatRotation)), chatAxis.x, chatAxis.y, chatAxis.z);
|
||||
|
||||
glColor3f(0.0f, 0.8f, 0.0f);
|
||||
glRotatef(180.0f, 0.0f, 1.0f, 0.0f);
|
||||
glRotatef(180.0f, 0.0f, 0.0f, 1.0f);
|
||||
glScalef(_scale * CHAT_MESSAGE_SCALE, _scale * CHAT_MESSAGE_SCALE, 1.0f);
|
||||
|
||||
glDisable(GL_LIGHTING);
|
||||
glDepthMask(false);
|
||||
if (_keyState == NO_KEY_DOWN) {
|
||||
textRenderer(CHAT)->draw(-width / 2.0f, 0, _chatMessage.c_str());
|
||||
|
||||
} else {
|
||||
// rather than using substr and allocating a new string, just replace the last
|
||||
// character with a null, then restore it
|
||||
int lastIndex = _chatMessage.size() - 1;
|
||||
char lastChar = _chatMessage[lastIndex];
|
||||
_chatMessage[lastIndex] = '\0';
|
||||
textRenderer(CHAT)->draw(-width / 2.0f, 0, _chatMessage.c_str());
|
||||
_chatMessage[lastIndex] = lastChar;
|
||||
glColor3f(0.0f, 1.0f, 0.0f);
|
||||
textRenderer(CHAT)->draw(width / 2.0f - lastWidth, 0, _chatMessage.c_str() + lastIndex);
|
||||
}
|
||||
glEnable(GL_LIGHTING);
|
||||
glDepthMask(true);
|
||||
|
||||
glPopMatrix();
|
||||
}
|
||||
}
|
||||
|
||||
glm::quat Avatar::computeRotationFromBodyToWorldUp(float proportion) const {
|
||||
|
|
|
@ -49,16 +49,22 @@ void FaceModel::maybeUpdateNeckRotation(const JointState& parentState, const FBX
|
|||
Avatar* owningAvatar = static_cast<Avatar*>(_owningHead->_owningAvatar);
|
||||
// get the rotation axes in joint space and use them to adjust the rotation
|
||||
glm::mat3 axes = glm::mat3_cast(glm::quat());
|
||||
glm::mat3 inverse = glm::mat3(glm::inverse(parentState.getTransform() * glm::translate(state.getDefaultTranslationInConstrainedFrame()) *
|
||||
joint.preTransform * glm::mat4_cast(joint.preRotation)));
|
||||
state.setRotationInConstrainedFrame(
|
||||
glm::angleAxis(- RADIANS_PER_DEGREE * (_owningHead->getFinalRoll() - owningAvatar->getHead()->getFinalLeanSideways()),
|
||||
glm::normalize(inverse * axes[2]))
|
||||
* glm::angleAxis(RADIANS_PER_DEGREE * (_owningHead->getFinalYaw() - _owningHead->getTorsoTwist()),
|
||||
glm::normalize(inverse * axes[1]))
|
||||
* glm::angleAxis(- RADIANS_PER_DEGREE * (_owningHead->getFinalPitch() - owningAvatar->getHead()->getFinalLeanForward()),
|
||||
glm::normalize(inverse * axes[0]))
|
||||
* joint.rotation, DEFAULT_PRIORITY);
|
||||
glm::mat3 inverse = glm::mat3(glm::inverse(parentState.getTransform() *
|
||||
glm::translate(state.getDefaultTranslationInConstrainedFrame()) *
|
||||
joint.preTransform * glm::mat4_cast(joint.preRotation)));
|
||||
glm::vec3 pitchYawRoll = safeEulerAngles(_owningHead->getFinalOrientationInLocalFrame());
|
||||
if (owningAvatar->isMyAvatar()) {
|
||||
glm::vec3 lean = glm::radians(glm::vec3(_owningHead->getFinalLeanForward(),
|
||||
_owningHead->getTorsoTwist(),
|
||||
_owningHead->getFinalLeanSideways()));
|
||||
pitchYawRoll -= lean;
|
||||
}
|
||||
|
||||
state.setRotationInConstrainedFrame(glm::angleAxis(-pitchYawRoll.z, glm::normalize(inverse * axes[2]))
|
||||
* glm::angleAxis(pitchYawRoll.y, glm::normalize(inverse * axes[1]))
|
||||
* glm::angleAxis(-pitchYawRoll.x, glm::normalize(inverse * axes[0]))
|
||||
* joint.rotation, DEFAULT_PRIORITY);
|
||||
|
||||
}
|
||||
|
||||
void FaceModel::maybeUpdateEyeRotation(Model* model, const JointState& parentState, const FBXJoint& joint, JointState& state) {
|
||||
|
|
|
@ -175,11 +175,6 @@ QByteArray AvatarData::toByteArray() {
|
|||
// Instantaneous audio loudness (used to drive facial animation)
|
||||
memcpy(destinationBuffer, &_headData->_audioLoudness, sizeof(float));
|
||||
destinationBuffer += sizeof(float);
|
||||
|
||||
// chat message
|
||||
*destinationBuffer++ = _chatMessage.size();
|
||||
memcpy(destinationBuffer, _chatMessage.data(), _chatMessage.size() * sizeof(char));
|
||||
destinationBuffer += _chatMessage.size() * sizeof(char);
|
||||
|
||||
// bitMask of less than byte wide items
|
||||
unsigned char bitItems = 0;
|
||||
|
@ -300,11 +295,10 @@ int AvatarData::parseDataAtOffset(const QByteArray& packet, int offset) {
|
|||
// lookAt = 12
|
||||
// audioLoudness = 4
|
||||
// }
|
||||
// + 1 byte for messageSize (0)
|
||||
// + 1 byte for pupilSize
|
||||
// + 1 byte for numJoints (0)
|
||||
// = 53 bytes
|
||||
int minPossibleSize = 53;
|
||||
int minPossibleSize = 52;
|
||||
|
||||
int maxAvailableSize = packet.size() - offset;
|
||||
if (minPossibleSize > maxAvailableSize) {
|
||||
|
@ -420,23 +414,6 @@ int AvatarData::parseDataAtOffset(const QByteArray& packet, int offset) {
|
|||
_headData->_audioLoudness = audioLoudness;
|
||||
} // 4 bytes
|
||||
|
||||
// chat
|
||||
int chatMessageSize = *sourceBuffer++;
|
||||
minPossibleSize += chatMessageSize;
|
||||
if (minPossibleSize > maxAvailableSize) {
|
||||
if (shouldLogError(now)) {
|
||||
qDebug() << "Malformed AvatarData packet before ChatMessage;"
|
||||
<< " displayName = '" << _displayName << "'"
|
||||
<< " minPossibleSize = " << minPossibleSize
|
||||
<< " maxAvailableSize = " << maxAvailableSize;
|
||||
}
|
||||
return maxAvailableSize;
|
||||
}
|
||||
{ // chat payload
|
||||
_chatMessage = string((char*)sourceBuffer, chatMessageSize);
|
||||
sourceBuffer += chatMessageSize * sizeof(char);
|
||||
} // 1 + chatMessageSize bytes
|
||||
|
||||
{ // bitFlags and face data
|
||||
unsigned char bitItems = *sourceBuffer++;
|
||||
|
||||
|
|
|
@ -32,17 +32,17 @@ typedef unsigned long long quint64;
|
|||
#include <glm/glm.hpp>
|
||||
#include <glm/gtc/quaternion.hpp>
|
||||
|
||||
#include <QtCore/QElapsedTimer>
|
||||
#include <QtCore/QByteArray>
|
||||
#include <QtCore/QHash>
|
||||
#include <QtCore/QObject>
|
||||
#include <QtCore/QStringList>
|
||||
#include <QtCore/QUrl>
|
||||
#include <QtCore/QVector>
|
||||
#include <QtCore/QVariantMap>
|
||||
#include <QByteArray>
|
||||
#include <QElapsedTimer>
|
||||
#include <QHash>
|
||||
#include <QObject>
|
||||
#include <QRect>
|
||||
#include <QScriptable>
|
||||
#include <QStringList>
|
||||
#include <QUrl>
|
||||
#include <QUuid>
|
||||
#include <QVariantMap>
|
||||
#include <QVector>
|
||||
|
||||
#include <CollisionInfo.h>
|
||||
#include <RegisteredMetaTypes.h>
|
||||
|
@ -130,7 +130,6 @@ class AvatarData : public QObject {
|
|||
Q_PROPERTY(float bodyYaw READ getBodyYaw WRITE setBodyYaw)
|
||||
Q_PROPERTY(float bodyPitch READ getBodyPitch WRITE setBodyPitch)
|
||||
Q_PROPERTY(float bodyRoll READ getBodyRoll WRITE setBodyRoll)
|
||||
Q_PROPERTY(QString chatMessage READ getQStringChatMessage WRITE setChatMessage)
|
||||
|
||||
Q_PROPERTY(glm::quat orientation READ getOrientation WRITE setOrientation)
|
||||
Q_PROPERTY(glm::quat headOrientation READ getHeadOrientation WRITE setHeadOrientation)
|
||||
|
@ -242,12 +241,6 @@ public:
|
|||
void setKeyState(KeyState s) { _keyState = s; }
|
||||
KeyState keyState() const { return _keyState; }
|
||||
|
||||
// chat message
|
||||
void setChatMessage(const std::string& msg) { _chatMessage = msg; }
|
||||
void setChatMessage(const QString& string) { _chatMessage = string.toLocal8Bit().constData(); }
|
||||
const std::string& setChatMessage() const { return _chatMessage; }
|
||||
QString getQStringChatMessage() { return QString(_chatMessage.data()); }
|
||||
|
||||
bool isChatCirclingEnabled() const { return _isChatCirclingEnabled; }
|
||||
const HeadData* getHeadData() const { return _headData; }
|
||||
const HandData* getHandData() const { return _handData; }
|
||||
|
@ -355,9 +348,6 @@ protected:
|
|||
// key state
|
||||
KeyState _keyState;
|
||||
|
||||
// chat message
|
||||
std::string _chatMessage;
|
||||
|
||||
bool _isChatCirclingEnabled;
|
||||
bool _forceFaceshiftConnected;
|
||||
bool _hasNewJointRotations; // set in AvatarData, cleared in Avatar
|
||||
|
@ -396,7 +386,6 @@ private:
|
|||
AvatarData(const AvatarData&);
|
||||
AvatarData& operator= (const AvatarData&);
|
||||
};
|
||||
|
||||
Q_DECLARE_METATYPE(AvatarData*)
|
||||
|
||||
class JointData {
|
||||
|
|
|
@ -57,7 +57,7 @@ PacketVersion versionForPacketType(PacketType type) {
|
|||
case PacketTypeInjectAudio:
|
||||
return 1;
|
||||
case PacketTypeAvatarData:
|
||||
return 3;
|
||||
return 4;
|
||||
case PacketTypeAvatarIdentity:
|
||||
return 1;
|
||||
case PacketTypeEnvironmentData:
|
||||
|
|
Loading…
Reference in a new issue