diff --git a/BUILD_WIN.md b/BUILD_WIN.md index 5836d5bfb5..90d2995e7d 100644 --- a/BUILD_WIN.md +++ b/BUILD_WIN.md @@ -39,7 +39,7 @@ Go to `Control Panel > System > Advanced System Settings > Environment Variables ### Step 6. Installing OpenSSL via vcpkg - * In the vcpkg directory, install the 64 bit OpenSSL package with the command `vcpkg install openssl:x64-windows` + * In the vcpkg directory, install the 64 bit OpenSSL package with the command `.\vcpkg install openssl:x64-windows` * Once the build completes you should have a file `ssl.h` in `${VCPKG_ROOT}/installed/x64-windows/include/openssl` ### Step 7. Running CMake to Generate Build Files diff --git a/android/app/build.gradle b/android/app/build.gradle index 3537df033d..980d197397 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -4,7 +4,7 @@ android { compileSdkVersion 26 //buildToolsVersion '27.0.3' - def appVersionCode = Integer.valueOf(RELEASE_NUMBER ?: 1) + def appVersionCode = Integer.valueOf(VERSION_CODE ?: 1) def appVersionName = RELEASE_NUMBER ?: "1.0" defaultConfig { diff --git a/android/build.gradle b/android/build.gradle index 373569ca77..39265327b2 100644 --- a/android/build.gradle +++ b/android/build.gradle @@ -37,6 +37,7 @@ task clean(type: Delete) { ext { RELEASE_NUMBER = project.hasProperty('RELEASE_NUMBER') ? project.getProperty('RELEASE_NUMBER') : '0' + VERSION_CODE = project.hasProperty('VERSION_CODE') ? project.getProperty('VERSION_CODE') : '0' RELEASE_TYPE = project.hasProperty('RELEASE_TYPE') ? project.getProperty('RELEASE_TYPE') : 'DEV' STABLE_BUILD = project.hasProperty('STABLE_BUILD') ? project.getProperty('STABLE_BUILD') : '0' EXEC_SUFFIX = Os.isFamily(Os.FAMILY_WINDOWS) ? '.exe' : '' diff --git a/assignment-client/src/entities/EntityTreeHeadlessViewer.cpp b/assignment-client/src/entities/EntityTreeHeadlessViewer.cpp index 81c42cda1e..3649cf1129 100644 --- a/assignment-client/src/entities/EntityTreeHeadlessViewer.cpp +++ b/assignment-client/src/entities/EntityTreeHeadlessViewer.cpp @@ -17,6 +17,9 @@ EntityTreeHeadlessViewer::EntityTreeHeadlessViewer() } EntityTreeHeadlessViewer::~EntityTreeHeadlessViewer() { + if (_simulation) { + _simulation->setEntityTree(nullptr); // Break shared_ptr cycle. + } } void EntityTreeHeadlessViewer::init() { diff --git a/assignment-client/src/scripts/EntityScriptServer.cpp b/assignment-client/src/scripts/EntityScriptServer.cpp index 607ab28b20..ebe25b11bf 100644 --- a/assignment-client/src/scripts/EntityScriptServer.cpp +++ b/assignment-client/src/scripts/EntityScriptServer.cpp @@ -69,9 +69,6 @@ EntityScriptServer::EntityScriptServer(ReceivedMessage& message) : ThreadedAssig DependencyManager::set(); DependencyManager::set(); - DependencyManager::set(ScriptEngine::ENTITY_SERVER_SCRIPT); - - DependencyManager::set(); // Needed to ensure the creation of the DebugDraw instance on the main thread @@ -254,6 +251,9 @@ void EntityScriptServer::handleEntityScriptCallMethodPacket(QSharedPointer(ScriptEngine::ENTITY_SERVER_SCRIPT); + DependencyManager::set(); + // make sure we request our script once the agent connects to the domain auto nodeList = DependencyManager::get(); @@ -571,6 +571,8 @@ void EntityScriptServer::aboutToFinish() { entityScriptingInterface->setPacketSender(nullptr); } + DependencyManager::destroy(); + DependencyManager::get()->cleanup(); DependencyManager::destroy(); diff --git a/cmake/macros/SetPackagingParameters.cmake b/cmake/macros/SetPackagingParameters.cmake index 2c8443d510..c40691c632 100644 --- a/cmake/macros/SetPackagingParameters.cmake +++ b/cmake/macros/SetPackagingParameters.cmake @@ -90,7 +90,7 @@ macro(SET_PACKAGING_PARAMETERS) # for the second parent of HEAD (not HEAD) since that is the # SHA of the commit merged to master for the build if (PR_BUILD) - set(_GIT_LOG_FORMAT "%p") + set(_GIT_LOG_FORMAT "%p %h") else () set(_GIT_LOG_FORMAT "%h") endif () diff --git a/domain-server/src/DomainGatekeeper.cpp b/domain-server/src/DomainGatekeeper.cpp index 2a6b78744e..59cc8d10f6 100644 --- a/domain-server/src/DomainGatekeeper.cpp +++ b/domain-server/src/DomainGatekeeper.cpp @@ -412,7 +412,7 @@ SharedNodePointer DomainGatekeeper::processAgentConnectRequest(const NodeConnect } else if (verifyUserSignature(username, usernameSignature, nodeConnection.senderSockAddr)) { // they sent us a username and the signature verifies it getGroupMemberships(username); - verifiedUsername = username; + verifiedUsername = username.toLower(); } else { // they sent us a username, but it didn't check out requestUserPublicKey(username); @@ -993,7 +993,7 @@ void DomainGatekeeper::getDomainOwnerFriendsListJSONCallback(QNetworkReply* requ _domainOwnerFriends.clear(); QJsonArray friends = jsonObject["data"].toObject()["friends"].toArray(); for (int i = 0; i < friends.size(); i++) { - _domainOwnerFriends += friends.at(i).toString(); + _domainOwnerFriends += friends.at(i).toString().toLower(); } } else { qDebug() << "getDomainOwnerFriendsList api call returned:" << QJsonDocument(jsonObject).toJson(QJsonDocument::Compact); diff --git a/interface/resources/html/img/tablet-help-keyboard.jpg b/interface/resources/html/img/tablet-help-keyboard.jpg index d0f84c17c7..1c257f83e2 100644 Binary files a/interface/resources/html/img/tablet-help-keyboard.jpg and b/interface/resources/html/img/tablet-help-keyboard.jpg differ diff --git a/interface/resources/qml/hifi/tablet/ControllerSettings.qml b/interface/resources/qml/hifi/tablet/ControllerSettings.qml index 4ad37b7bc8..92b750fa7a 100644 --- a/interface/resources/qml/hifi/tablet/ControllerSettings.qml +++ b/interface/resources/qml/hifi/tablet/ControllerSettings.qml @@ -69,6 +69,7 @@ Item { id: stack initialItem: inputConfiguration property alias messageVisible: imageMessageBox.visible + property string selectedPlugin: "" Rectangle { id: inputConfiguration anchors { @@ -274,6 +275,8 @@ Item { } else { box.label = ""; } + + stack.selectedPlugin = selectedDevice; } Timer { diff --git a/interface/resources/qml/hifi/tablet/OpenVrConfiguration.qml b/interface/resources/qml/hifi/tablet/OpenVrConfiguration.qml index 20682372c5..c2aff08e35 100644 --- a/interface/resources/qml/hifi/tablet/OpenVrConfiguration.qml +++ b/interface/resources/qml/hifi/tablet/OpenVrConfiguration.qml @@ -28,6 +28,7 @@ Flickable { onPluginNameChanged: { if (page !== null) { page.pluginName = flick.pluginName; + page.displayConfiguration(); } } diff --git a/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml b/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml index 08f86770e6..9a472de046 100644 --- a/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml +++ b/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml @@ -89,6 +89,7 @@ StackView { property bool keyboardEnabled: false property bool punctuationMode: false + property bool keyboardRaised: false width: parent.width height: parent.height @@ -210,6 +211,8 @@ StackView { QQC2.TextField { id: addressLine + + focus: true width: addressLineContainer.width - addressLineContainer.anchors.leftMargin - addressLineContainer.anchors.rightMargin; anchors { left: addressLineContainer.left; @@ -236,24 +239,20 @@ StackView { color: hifi.colors.text background: Item {} - QQC2.Label { - T.TextField { - id: control + } - padding: 6 // numbers taken from Qt\5.9.2\Src\qtquickcontrols2\src\imports\controls\TextField.qml - leftPadding: padding + 4 - } + QQC2.Label { + font: addressLine.font - font: parent.font + x: addressLine.x + y: addressLine.y + leftPadding: addressLine.leftPadding + topPadding: addressLine.topPadding - x: control.leftPadding - y: control.topPadding - - text: parent.placeholderText2 - verticalAlignment: "AlignVCenter" - color: 'gray' - visible: parent.text === '' - } + text: addressLine.placeholderText2 + verticalAlignment: "AlignVCenter" + color: 'gray' + visible: addressLine.text === '' } Rectangle { diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 5decbd2e60..9fd542e4ce 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -2723,7 +2723,7 @@ void Application::initializeDisplayPlugins() { setDisplayPlugin(defaultDisplayPlugin); // Now set the desired plugin if it's not the same as the default plugin - if (!targetDisplayPlugin && (targetDisplayPlugin != defaultDisplayPlugin)) { + if (targetDisplayPlugin && (targetDisplayPlugin != defaultDisplayPlugin)) { setDisplayPlugin(targetDisplayPlugin); } @@ -6998,7 +6998,9 @@ void Application::showAssetServerWidget(QString filePath) { DependencyManager::get()->show(url, "AssetServer", startUpload); } else { static const QUrl url("hifi/dialogs/TabletAssetServer.qml"); - tablet->pushOntoStack(url); + if (!tablet->isPathLoaded(url)) { + tablet->pushOntoStack(url); + } } } diff --git a/interface/src/Menu.cpp b/interface/src/Menu.cpp index fcf7b53536..646067169f 100644 --- a/interface/src/Menu.cpp +++ b/interface/src/Menu.cpp @@ -256,8 +256,6 @@ Menu::Menu() { addCheckableActionToQMenuAndActionHash(viewMenu, MenuOption::CenterPlayerInView, 0, true, qApp, SLOT(rotationModeChanged())); - addCheckableActionToQMenuAndActionHash(viewMenu, MenuOption::Overlays, 0, true); - // View > Enter First Person Mode in HMD addCheckableActionToQMenuAndActionHash(viewMenu, MenuOption::FirstPersonHMD, 0, true); @@ -818,6 +816,9 @@ Menu::Menu() { addCheckableActionToQMenuAndActionHash(developerMenu, MenuOption::VerboseLogging, 0, false, qApp, SLOT(updateVerboseLogging())); + // Developer > Show Overlays + addCheckableActionToQMenuAndActionHash(developerMenu, MenuOption::Overlays, 0, true); + #if 0 /// -------------- REMOVED FOR NOW -------------- addDisabledActionAndSeparator(navigateMenu, "History"); QAction* backAction = addActionToQMenuAndActionHash(navigateMenu, MenuOption::Back, 0, addressManager.data(), SLOT(goBack())); diff --git a/interface/src/avatar/MyAvatar.cpp b/interface/src/avatar/MyAvatar.cpp index ed7ce87db2..b08496c2b8 100755 --- a/interface/src/avatar/MyAvatar.cpp +++ b/interface/src/avatar/MyAvatar.cpp @@ -3348,7 +3348,7 @@ void MyAvatar::FollowHelper::prePhysicsUpdate(MyAvatar& myAvatar, const glm::mat if (!isActive(Rotation) && (shouldActivateRotation(myAvatar, desiredBodyMatrix, currentBodyMatrix) || hasDriveInput)) { activate(Rotation); } - if (!isActive(Horizontal) && shouldActivateHorizontal(myAvatar, desiredBodyMatrix, currentBodyMatrix)) { + if (!isActive(Horizontal) && (shouldActivateHorizontal(myAvatar, desiredBodyMatrix, currentBodyMatrix) || hasDriveInput)) { activate(Horizontal); } if (!isActive(Vertical) && (shouldActivateVertical(myAvatar, desiredBodyMatrix, currentBodyMatrix) || hasDriveInput)) { diff --git a/interface/src/avatar/MySkeletonModel.cpp b/interface/src/avatar/MySkeletonModel.cpp index c15b00ca19..0fc5e7521e 100644 --- a/interface/src/avatar/MySkeletonModel.cpp +++ b/interface/src/avatar/MySkeletonModel.cpp @@ -46,7 +46,7 @@ static AnimPose computeHipsInSensorFrame(MyAvatar* myAvatar, bool isFlying) { } glm::mat4 hipsMat; - if (myAvatar->getCenterOfGravityModelEnabled()) { + if (myAvatar->getCenterOfGravityModelEnabled() && !isFlying) { // then we use center of gravity model hipsMat = myAvatar->deriveBodyUsingCgModel(); } else { @@ -109,6 +109,11 @@ void MySkeletonModel::updateRig(float deltaTime, glm::mat4 parentTransform) { AnimPose avatarToRigPose(glm::vec3(1.0f), Quaternions::Y_180, glm::vec3(0.0f)); + glm::mat4 rigToAvatarMatrix = Matrices::Y_180; + glm::mat4 avatarToWorldMatrix = createMatFromQuatAndPos(myAvatar->getWorldOrientation(), myAvatar->getWorldPosition()); + glm::mat4 sensorToWorldMatrix = myAvatar->getSensorToWorldMatrix(); + params.rigToSensorMatrix = glm::inverse(sensorToWorldMatrix) * avatarToWorldMatrix * rigToAvatarMatrix; + // input action is the highest priority source for head orientation. auto avatarHeadPose = myAvatar->getControllerPoseInAvatarFrame(controller::Action::HEAD); if (avatarHeadPose.isValid()) { diff --git a/libraries/animation/src/Rig.cpp b/libraries/animation/src/Rig.cpp index 0833b28142..549989778e 100644 --- a/libraries/animation/src/Rig.cpp +++ b/libraries/animation/src/Rig.cpp @@ -1244,7 +1244,8 @@ void Rig::updateHands(bool leftHandEnabled, bool rightHandEnabled, bool hipsEnab bool leftArmEnabled, bool rightArmEnabled, float dt, const AnimPose& leftHandPose, const AnimPose& rightHandPose, const FBXJointShapeInfo& hipsShapeInfo, const FBXJointShapeInfo& spineShapeInfo, - const FBXJointShapeInfo& spine1ShapeInfo, const FBXJointShapeInfo& spine2ShapeInfo) { + const FBXJointShapeInfo& spine1ShapeInfo, const FBXJointShapeInfo& spine2ShapeInfo, + const glm::mat4& rigToSensorMatrix, const glm::mat4& sensorToRigMatrix) { const bool ENABLE_POLE_VECTORS = false; const float ELBOW_POLE_VECTOR_BLEND_FACTOR = 0.95f; @@ -1271,19 +1272,20 @@ void Rig::updateHands(bool leftHandEnabled, bool rightHandEnabled, bool hipsEnab int elbowJointIndex = _animSkeleton->nameToJointIndex("LeftForeArm"); if (ENABLE_POLE_VECTORS && !leftArmEnabled && handJointIndex >= 0 && armJointIndex >= 0 && elbowJointIndex >= 0) { glm::vec3 poleVector = calculateElbowPoleVector(handJointIndex, elbowJointIndex, armJointIndex, hipsIndex, true); + glm::vec3 sensorPoleVector = transformVectorFast(rigToSensorMatrix, poleVector); // smooth toward desired pole vector from previous pole vector... to reduce jitter if (!_prevLeftHandPoleVectorValid) { _prevLeftHandPoleVectorValid = true; - _prevLeftHandPoleVector = poleVector; + _prevLeftHandPoleVector = sensorPoleVector; } - glm::quat deltaRot = rotationBetween(_prevLeftHandPoleVector, poleVector); + glm::quat deltaRot = rotationBetween(_prevLeftHandPoleVector, sensorPoleVector); glm::quat smoothDeltaRot = safeMix(deltaRot, Quaternions::IDENTITY, ELBOW_POLE_VECTOR_BLEND_FACTOR); _prevLeftHandPoleVector = smoothDeltaRot * _prevLeftHandPoleVector; _animVars.set("leftHandPoleVectorEnabled", true); _animVars.set("leftHandPoleReferenceVector", Vectors::UNIT_X); - _animVars.set("leftHandPoleVector", _prevLeftHandPoleVector); + _animVars.set("leftHandPoleVector", transformVectorFast(sensorToRigMatrix, _prevLeftHandPoleVector)); } else { _prevLeftHandPoleVectorValid = false; _animVars.set("leftHandPoleVectorEnabled", false); @@ -1318,19 +1320,20 @@ void Rig::updateHands(bool leftHandEnabled, bool rightHandEnabled, bool hipsEnab int elbowJointIndex = _animSkeleton->nameToJointIndex("RightForeArm"); if (ENABLE_POLE_VECTORS && !rightArmEnabled && handJointIndex >= 0 && armJointIndex >= 0 && elbowJointIndex >= 0) { glm::vec3 poleVector = calculateElbowPoleVector(handJointIndex, elbowJointIndex, armJointIndex, hipsIndex, false); + glm::vec3 sensorPoleVector = transformVectorFast(rigToSensorMatrix, poleVector); // smooth toward desired pole vector from previous pole vector... to reduce jitter if (!_prevRightHandPoleVectorValid) { _prevRightHandPoleVectorValid = true; - _prevRightHandPoleVector = poleVector; + _prevRightHandPoleVector = sensorPoleVector; } - glm::quat deltaRot = rotationBetween(_prevRightHandPoleVector, poleVector); + glm::quat deltaRot = rotationBetween(_prevRightHandPoleVector, sensorPoleVector); glm::quat smoothDeltaRot = safeMix(deltaRot, Quaternions::IDENTITY, ELBOW_POLE_VECTOR_BLEND_FACTOR); _prevRightHandPoleVector = smoothDeltaRot * _prevRightHandPoleVector; _animVars.set("rightHandPoleVectorEnabled", true); _animVars.set("rightHandPoleReferenceVector", -Vectors::UNIT_X); - _animVars.set("rightHandPoleVector", _prevRightHandPoleVector); + _animVars.set("rightHandPoleVector", transformVectorFast(sensorToRigMatrix, _prevRightHandPoleVector)); } else { _prevRightHandPoleVectorValid = false; _animVars.set("rightHandPoleVectorEnabled", false); @@ -1345,7 +1348,8 @@ void Rig::updateHands(bool leftHandEnabled, bool rightHandEnabled, bool hipsEnab } } -void Rig::updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose& leftFootPose, const AnimPose& rightFootPose) { +void Rig::updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose& leftFootPose, const AnimPose& rightFootPose, + const glm::mat4& rigToSensorMatrix, const glm::mat4& sensorToRigMatrix) { const float KNEE_POLE_VECTOR_BLEND_FACTOR = 0.95f; @@ -1360,19 +1364,20 @@ void Rig::updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose int kneeJointIndex = _animSkeleton->nameToJointIndex("LeftLeg"); int upLegJointIndex = _animSkeleton->nameToJointIndex("LeftUpLeg"); glm::vec3 poleVector = calculateKneePoleVector(footJointIndex, kneeJointIndex, upLegJointIndex, hipsIndex, leftFootPose); + glm::vec3 sensorPoleVector = transformVectorFast(rigToSensorMatrix, poleVector); - // smooth toward desired pole vector from previous pole vector... to reduce jitter + // smooth toward desired pole vector from previous pole vector... to reduce jitter, but in sensor space. if (!_prevLeftFootPoleVectorValid) { _prevLeftFootPoleVectorValid = true; - _prevLeftFootPoleVector = poleVector; + _prevLeftFootPoleVector = sensorPoleVector; } - glm::quat deltaRot = rotationBetween(_prevLeftFootPoleVector, poleVector); + glm::quat deltaRot = rotationBetween(_prevLeftFootPoleVector, sensorPoleVector); glm::quat smoothDeltaRot = safeMix(deltaRot, Quaternions::IDENTITY, KNEE_POLE_VECTOR_BLEND_FACTOR); _prevLeftFootPoleVector = smoothDeltaRot * _prevLeftFootPoleVector; _animVars.set("leftFootPoleVectorEnabled", true); _animVars.set("leftFootPoleReferenceVector", Vectors::UNIT_Z); - _animVars.set("leftFootPoleVector", _prevLeftFootPoleVector); + _animVars.set("leftFootPoleVector", transformVectorFast(sensorToRigMatrix, _prevLeftFootPoleVector)); } else { _animVars.unset("leftFootPosition"); _animVars.unset("leftFootRotation"); @@ -1390,19 +1395,20 @@ void Rig::updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose int kneeJointIndex = _animSkeleton->nameToJointIndex("RightLeg"); int upLegJointIndex = _animSkeleton->nameToJointIndex("RightUpLeg"); glm::vec3 poleVector = calculateKneePoleVector(footJointIndex, kneeJointIndex, upLegJointIndex, hipsIndex, rightFootPose); + glm::vec3 sensorPoleVector = transformVectorFast(rigToSensorMatrix, poleVector); // smooth toward desired pole vector from previous pole vector... to reduce jitter if (!_prevRightFootPoleVectorValid) { _prevRightFootPoleVectorValid = true; - _prevRightFootPoleVector = poleVector; + _prevRightFootPoleVector = sensorPoleVector; } - glm::quat deltaRot = rotationBetween(_prevRightFootPoleVector, poleVector); + glm::quat deltaRot = rotationBetween(_prevRightFootPoleVector, sensorPoleVector); glm::quat smoothDeltaRot = safeMix(deltaRot, Quaternions::IDENTITY, KNEE_POLE_VECTOR_BLEND_FACTOR); _prevRightFootPoleVector = smoothDeltaRot * _prevRightFootPoleVector; _animVars.set("rightFootPoleVectorEnabled", true); _animVars.set("rightFootPoleReferenceVector", Vectors::UNIT_Z); - _animVars.set("rightFootPoleVector", _prevRightFootPoleVector); + _animVars.set("rightFootPoleVector", transformVectorFast(sensorToRigMatrix, _prevRightFootPoleVector)); } else { _animVars.unset("rightFootPosition"); _animVars.unset("rightFootRotation"); @@ -1434,9 +1440,9 @@ void Rig::updateEyeJoint(int index, const glm::vec3& modelTranslation, const glm glm::quat deltaQuat = desiredQuat * glm::inverse(headQuat); - // limit swing rotation of the deltaQuat by a 30 degree cone. + // limit swing rotation of the deltaQuat by a 25 degree cone. // TODO: use swing twist decomposition constraint instead, for off axis rotation clamping. - const float MAX_ANGLE = 30.0f * RADIANS_PER_DEGREE; + const float MAX_ANGLE = 25.0f * RADIANS_PER_DEGREE; if (fabsf(glm::angle(deltaQuat)) > MAX_ANGLE) { deltaQuat = glm::angleAxis(glm::clamp(glm::angle(deltaQuat), -MAX_ANGLE, MAX_ANGLE), glm::axis(deltaQuat)); } @@ -1546,16 +1552,18 @@ void Rig::updateFromControllerParameters(const ControllerParameters& params, flo bool spine2Enabled = params.primaryControllerFlags[PrimaryControllerType_Spine2] & (uint8_t)ControllerFlags::Enabled; bool leftArmEnabled = params.secondaryControllerFlags[SecondaryControllerType_LeftArm] & (uint8_t)ControllerFlags::Enabled; bool rightArmEnabled = params.secondaryControllerFlags[SecondaryControllerType_RightArm] & (uint8_t)ControllerFlags::Enabled; + glm::mat4 sensorToRigMatrix = glm::inverse(params.rigToSensorMatrix); updateHead(headEnabled, hipsEnabled, params.primaryControllerPoses[PrimaryControllerType_Head]); updateHands(leftHandEnabled, rightHandEnabled, hipsEnabled, hipsEstimated, leftArmEnabled, rightArmEnabled, dt, params.primaryControllerPoses[PrimaryControllerType_LeftHand], params.primaryControllerPoses[PrimaryControllerType_RightHand], - params.hipsShapeInfo, params.spineShapeInfo, params.spine1ShapeInfo, params.spine2ShapeInfo); + params.hipsShapeInfo, params.spineShapeInfo, params.spine1ShapeInfo, params.spine2ShapeInfo, + params.rigToSensorMatrix, sensorToRigMatrix); updateFeet(leftFootEnabled, rightFootEnabled, - params.primaryControllerPoses[PrimaryControllerType_LeftFoot], params.primaryControllerPoses[PrimaryControllerType_RightFoot]); - + params.primaryControllerPoses[PrimaryControllerType_LeftFoot], params.primaryControllerPoses[PrimaryControllerType_RightFoot], + params.rigToSensorMatrix, sensorToRigMatrix); if (headEnabled) { // Blend IK chains toward the joint limit centers, this should stablize head and hand ik. diff --git a/libraries/animation/src/Rig.h b/libraries/animation/src/Rig.h index e30b5d655c..ffa3a128b9 100644 --- a/libraries/animation/src/Rig.h +++ b/libraries/animation/src/Rig.h @@ -75,6 +75,7 @@ public: }; struct ControllerParameters { + glm::mat4 rigToSensorMatrix; AnimPose primaryControllerPoses[NumPrimaryControllerTypes]; // rig space uint8_t primaryControllerFlags[NumPrimaryControllerTypes]; AnimPose secondaryControllerPoses[NumSecondaryControllerTypes]; // rig space @@ -231,8 +232,10 @@ protected: bool leftArmEnabled, bool rightArmEnabled, float dt, const AnimPose& leftHandPose, const AnimPose& rightHandPose, const FBXJointShapeInfo& hipsShapeInfo, const FBXJointShapeInfo& spineShapeInfo, - const FBXJointShapeInfo& spine1ShapeInfo, const FBXJointShapeInfo& spine2ShapeInfo); - void updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose& leftFootPose, const AnimPose& rightFootPose); + const FBXJointShapeInfo& spine1ShapeInfo, const FBXJointShapeInfo& spine2ShapeInfo, + const glm::mat4& rigToSensorMatrix, const glm::mat4& sensorToRigMatrix); + void updateFeet(bool leftFootEnabled, bool rightFootEnabled, const AnimPose& leftFootPose, const AnimPose& rightFootPose, + const glm::mat4& rigToSensorMatrix, const glm::mat4& sensorToRigMatrix); void updateEyeJoint(int index, const glm::vec3& modelTranslation, const glm::quat& modelRotation, const glm::vec3& lookAt, const glm::vec3& saccade); void calcAnimAlpha(float speed, const std::vector& referenceSpeeds, float* alphaOut) const; @@ -359,16 +362,16 @@ protected: int _nextStateHandlerId { 0 }; QMutex _stateMutex; - glm::vec3 _prevRightFootPoleVector { Vectors::UNIT_Z }; + glm::vec3 _prevRightFootPoleVector { Vectors::UNIT_Z }; // sensor space bool _prevRightFootPoleVectorValid { false }; - glm::vec3 _prevLeftFootPoleVector { Vectors::UNIT_Z }; + glm::vec3 _prevLeftFootPoleVector { Vectors::UNIT_Z }; // sensor space bool _prevLeftFootPoleVectorValid { false }; - glm::vec3 _prevRightHandPoleVector { -Vectors::UNIT_Z }; + glm::vec3 _prevRightHandPoleVector { -Vectors::UNIT_Z }; // sensor space bool _prevRightHandPoleVectorValid { false }; - glm::vec3 _prevLeftHandPoleVector { -Vectors::UNIT_Z }; + glm::vec3 _prevLeftHandPoleVector { -Vectors::UNIT_Z }; // sensor space bool _prevLeftHandPoleVectorValid { false }; int _rigId; diff --git a/libraries/avatars-renderer/src/avatars-renderer/Head.cpp b/libraries/avatars-renderer/src/avatars-renderer/Head.cpp index 5800c1404b..bdee6d9147 100644 --- a/libraries/avatars-renderer/src/avatars-renderer/Head.cpp +++ b/libraries/avatars-renderer/src/avatars-renderer/Head.cpp @@ -220,30 +220,44 @@ void Head::calculateMouthShapes(float deltaTime) { void Head::applyEyelidOffset(glm::quat headOrientation) { // Adjusts the eyelid blendshape coefficients so that the eyelid follows the iris as the head pitches. - - if (disableEyelidAdjustment) { + bool isBlinking = (_rightEyeBlinkVelocity != 0.0f && _rightEyeBlinkVelocity != 0.0f); + if (disableEyelidAdjustment || isBlinking) { return; } - glm::quat eyeRotation = rotationBetween(headOrientation * IDENTITY_FORWARD, getLookAtPosition() - _eyePosition); - eyeRotation = eyeRotation * glm::angleAxis(safeEulerAngles(headOrientation).y, IDENTITY_UP); // Rotation w.r.t. head - float eyePitch = safeEulerAngles(eyeRotation).x; + const float EYE_PITCH_TO_COEFFICIENT = 3.5f; // Empirically determined + const float MAX_EYELID_OFFSET = 1.5f; + const float BLINK_DOWN_MULTIPLIER = 0.25f; + const float OPEN_DOWN_MULTIPLIER = 0.3f; + const float BROW_UP_MULTIPLIER = 0.5f; - const float EYE_PITCH_TO_COEFFICIENT = 1.6f; // Empirically determined - const float MAX_EYELID_OFFSET = 0.8f; // So that don't fully close eyes when looking way down - float eyelidOffset = glm::clamp(-eyePitch * EYE_PITCH_TO_COEFFICIENT, -1.0f, MAX_EYELID_OFFSET); + glm::vec3 lookAt = glm::normalize(getLookAtPosition() - _eyePosition); + glm::vec3 headUp = headOrientation * Vectors::UNIT_Y; + float eyePitch = (PI / 2.0f) - acos(glm::dot(lookAt, headUp)); + float eyelidOffset = glm::clamp(abs(eyePitch * EYE_PITCH_TO_COEFFICIENT), 0.0f, MAX_EYELID_OFFSET); - for (int i = 0; i < 2; i++) { - const int LEFT_EYE = 8; - float eyeCoefficient = _transientBlendshapeCoefficients[i] - _transientBlendshapeCoefficients[LEFT_EYE + i]; - eyeCoefficient = glm::clamp(eyelidOffset + eyeCoefficient * (1.0f - eyelidOffset), -1.0f, 1.0f); - if (eyeCoefficient > 0.0f) { - _transientBlendshapeCoefficients[i] = eyeCoefficient; - _transientBlendshapeCoefficients[LEFT_EYE + i] = 0.0f; + float blinkUpCoefficient = -eyelidOffset; + float blinkDownCoefficient = BLINK_DOWN_MULTIPLIER * eyelidOffset; + + float openUpCoefficient = eyelidOffset; + float openDownCoefficient = OPEN_DOWN_MULTIPLIER * eyelidOffset; + + float browsUpCoefficient = BROW_UP_MULTIPLIER * eyelidOffset; + float browsDownCoefficient = 0.0f; - } else { - _transientBlendshapeCoefficients[i] = 0.0f; - _transientBlendshapeCoefficients[LEFT_EYE + i] = -eyeCoefficient; + bool isLookingUp = (eyePitch > 0); + + if (isLookingUp) { + for (int i = 0; i < 2; i++) { + _transientBlendshapeCoefficients[EYE_BLINK_INDICES[i]] = blinkUpCoefficient; + _transientBlendshapeCoefficients[EYE_OPEN_INDICES[i]] = openUpCoefficient; + _transientBlendshapeCoefficients[BROWS_U_INDICES[i]] = browsUpCoefficient; + } + } else { + for (int i = 0; i < 2; i++) { + _transientBlendshapeCoefficients[EYE_BLINK_INDICES[i]] = blinkDownCoefficient; + _transientBlendshapeCoefficients[EYE_OPEN_INDICES[i]] = openDownCoefficient; + _transientBlendshapeCoefficients[BROWS_U_INDICES[i]] = browsDownCoefficient; } } } diff --git a/libraries/avatars/src/HeadData.cpp b/libraries/avatars/src/HeadData.cpp index 4119d7a459..19f5efcd16 100644 --- a/libraries/avatars/src/HeadData.cpp +++ b/libraries/avatars/src/HeadData.cpp @@ -17,7 +17,6 @@ #include #include -#include #include #include @@ -33,7 +32,7 @@ HeadData::HeadData(AvatarData* owningAvatar) : _summedBlendshapeCoefficients(QVector(0, 0.0f)), _owningAvatar(owningAvatar) { - + computeBlendshapesLookupMap(); } glm::quat HeadData::getRawOrientation() const { @@ -71,16 +70,10 @@ void HeadData::setOrientation(const glm::quat& orientation) { setHeadOrientation(orientation); } -//Lazily construct a lookup map from the blendshapes -static const QMap& getBlendshapesLookupMap() { - static std::once_flag once; - static QMap blendshapeLookupMap; - std::call_once(once, [&] { - for (int i = 0; i < NUM_FACESHIFT_BLENDSHAPES; i++) { - blendshapeLookupMap[FACESHIFT_BLENDSHAPES[i]] = i; - } - }); - return blendshapeLookupMap; +void HeadData::computeBlendshapesLookupMap(){ + for (int i = 0; i < NUM_FACESHIFT_BLENDSHAPES; i++) { + _blendshapeLookupMap[FACESHIFT_BLENDSHAPES[i]] = i; + } } int HeadData::getNumSummedBlendshapeCoefficients() const { @@ -108,11 +101,10 @@ const QVector& HeadData::getSummedBlendshapeCoefficients() { } void HeadData::setBlendshape(QString name, float val) { - const auto& blendshapeLookupMap = getBlendshapesLookupMap(); //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()) { + auto it = _blendshapeLookupMap.find(name); + if (it != _blendshapeLookupMap.end()) { if (_blendshapeCoefficients.size() <= it.value()) { _blendshapeCoefficients.resize(it.value() + 1); } @@ -123,6 +115,18 @@ void HeadData::setBlendshape(QString name, float val) { } } +int HeadData::getBlendshapeIndex(const QString& name) { + auto it = _blendshapeLookupMap.find(name); + int index = it != _blendshapeLookupMap.end() ? it.value() : -1; + return index; +} + +void HeadData::getBlendshapeIndices(const std::vector& blendShapeNames, std::vector& indexes) { + for (auto& name : blendShapeNames) { + indexes.push_back(getBlendshapeIndex(name)); + } +} + static const QString JSON_AVATAR_HEAD_ROTATION = QStringLiteral("rotation"); static const QString JSON_AVATAR_HEAD_BLENDSHAPE_COEFFICIENTS = QStringLiteral("blendShapes"); static const QString JSON_AVATAR_HEAD_LEAN_FORWARD = QStringLiteral("leanForward"); @@ -131,10 +135,9 @@ static const QString JSON_AVATAR_HEAD_LOOKAT = QStringLiteral("lookAt"); QJsonObject HeadData::toJson() const { QJsonObject headJson; - const auto& blendshapeLookupMap = getBlendshapesLookupMap(); QJsonObject blendshapesJson; - for (auto name : blendshapeLookupMap.keys()) { - auto index = blendshapeLookupMap[name]; + for (auto name : _blendshapeLookupMap.keys()) { + auto index = _blendshapeLookupMap[name]; float value = 0.0f; if (index < _blendshapeCoefficients.size()) { value += _blendshapeCoefficients[index]; diff --git a/libraries/avatars/src/HeadData.h b/libraries/avatars/src/HeadData.h index f9c4b52139..6d211da2cd 100644 --- a/libraries/avatars/src/HeadData.h +++ b/libraries/avatars/src/HeadData.h @@ -20,6 +20,7 @@ #include #include +#include // degrees const float MIN_HEAD_YAW = -180.0f; @@ -55,6 +56,8 @@ public: void setOrientation(const glm::quat& orientation); void setBlendshape(QString name, float val); + int getBlendshapeIndex(const QString& name); + void getBlendshapeIndices(const std::vector& blendShapeNames, std::vector& indexes); const QVector& getBlendshapeCoefficients() const { return _blendshapeCoefficients; } const QVector& getSummedBlendshapeCoefficients(); int getNumSummedBlendshapeCoefficients() const; @@ -114,6 +117,7 @@ protected: QVector _blendshapeCoefficients; QVector _transientBlendshapeCoefficients; QVector _summedBlendshapeCoefficients; + QMap _blendshapeLookupMap; AvatarData* _owningAvatar; private: @@ -122,6 +126,7 @@ private: HeadData& operator= (const HeadData&); void setHeadOrientation(const glm::quat& orientation); + void computeBlendshapesLookupMap(); }; #endif // hifi_HeadData_h diff --git a/libraries/entities/src/SimpleEntitySimulation.cpp b/libraries/entities/src/SimpleEntitySimulation.cpp index 3ed84035ac..28dc7b26c4 100644 --- a/libraries/entities/src/SimpleEntitySimulation.cpp +++ b/libraries/entities/src/SimpleEntitySimulation.cpp @@ -100,7 +100,7 @@ void SimpleEntitySimulation::changeEntityInternal(EntityItemPointer entity) { } } else if (entity->isMovingRelativeToParent()) { SetOfEntities::iterator itr = _simpleKinematicEntities.find(entity); - if (itr != _simpleKinematicEntities.end()) { + if (itr == _simpleKinematicEntities.end()) { _simpleKinematicEntities.insert(entity); entity->setLastSimulated(usecTimestampNow()); } @@ -118,7 +118,7 @@ void SimpleEntitySimulation::changeEntityInternal(EntityItemPointer entity) { if (entity->isMovingRelativeToParent()) { SetOfEntities::iterator itr = _simpleKinematicEntities.find(entity); - if (itr != _simpleKinematicEntities.end()) { + if (itr == _simpleKinematicEntities.end()) { _simpleKinematicEntities.insert(entity); entity->setLastSimulated(usecTimestampNow()); } diff --git a/libraries/gpu-gl-common/src/gpu/gl/GLBackendPipeline.cpp b/libraries/gpu-gl-common/src/gpu/gl/GLBackendPipeline.cpp index b75f89f7ae..adea3292e1 100644 --- a/libraries/gpu-gl-common/src/gpu/gl/GLBackendPipeline.cpp +++ b/libraries/gpu-gl-common/src/gpu/gl/GLBackendPipeline.cpp @@ -48,12 +48,12 @@ void GLBackend::do_setPipeline(const Batch& batch, size_t paramOffset) { return; } - // check the program cache - // pick the program version - // check the program cache - // pick the program version + // check the program cache + // pick the program version + // check the program cache + // pick the program version #ifdef GPU_STEREO_CAMERA_BUFFER - GLuint glprogram = pipelineObject->_program->getProgram((GLShader::Version) isStereo()); + GLuint glprogram = pipelineObject->_program->getProgram((GLShader::Version)isStereo()); #else GLuint glprogram = pipelineObject->_program->getProgram(); #endif @@ -85,10 +85,11 @@ void GLBackend::do_setPipeline(const Batch& batch, size_t paramOffset) { } else { cameraCorrectionBuffer = syncGPUObject(*_pipeline._cameraCorrectionBufferIdentity._buffer); } + // Invalidate uniform buffer cache slot + _uniform._buffers[_pipeline._cameraCorrectionLocation].reset(); glBindBufferRange(GL_UNIFORM_BUFFER, _pipeline._cameraCorrectionLocation, cameraCorrectionBuffer->_id, 0, sizeof(CameraCorrection)); - } - (void) CHECK_GL_ERROR(); + (void)CHECK_GL_ERROR(); _pipeline._invalidProgram = false; } } @@ -97,7 +98,7 @@ void GLBackend::updatePipeline() { if (_pipeline._invalidProgram) { // doing it here is aproblem for calls to glUniform.... so will do it on assing... glUseProgram(_pipeline._program); - (void) CHECK_GL_ERROR(); + (void)CHECK_GL_ERROR(); _pipeline._invalidProgram = false; } @@ -106,12 +107,12 @@ void GLBackend::updatePipeline() { // first reset to default what should be // the fields which were not to default and are default now resetPipelineState(_pipeline._state->_signature); - + // Update the signature cache with what's going to be touched _pipeline._stateSignatureCache |= _pipeline._state->_signature; // And perform - for (auto command: _pipeline._state->_commands) { + for (auto command : _pipeline._state->_commands) { command->run(this); } } else { @@ -142,8 +143,8 @@ void GLBackend::releaseUniformBuffer(uint32_t slot) { if (buf) { auto* object = Backend::getGPUObject(*buf); if (object) { - glBindBufferBase(GL_UNIFORM_BUFFER, slot, 0); // RELEASE - (void) CHECK_GL_ERROR(); + glBindBufferBase(GL_UNIFORM_BUFFER, slot, 0); // RELEASE + (void)CHECK_GL_ERROR(); } buf.reset(); } @@ -157,8 +158,9 @@ void GLBackend::resetUniformStage() { void GLBackend::do_setUniformBuffer(const Batch& batch, size_t paramOffset) { GLuint slot = batch._params[paramOffset + 3]._uint; - if (slot >(GLuint)MAX_NUM_UNIFORM_BUFFERS) { - qCDebug(gpugllogging) << "GLBackend::do_setUniformBuffer: Trying to set a uniform Buffer at slot #" << slot << " which doesn't exist. MaxNumUniformBuffers = " << getMaxNumUniformBuffers(); + if (slot > (GLuint)MAX_NUM_UNIFORM_BUFFERS) { + qCDebug(gpugllogging) << "GLBackend::do_setUniformBuffer: Trying to set a uniform Buffer at slot #" << slot + << " which doesn't exist. MaxNumUniformBuffers = " << getMaxNumUniformBuffers(); return; } BufferPointer uniformBuffer = batch._buffers.get(batch._params[paramOffset + 2]._uint); @@ -169,7 +171,7 @@ void GLBackend::do_setUniformBuffer(const Batch& batch, size_t paramOffset) { releaseUniformBuffer(slot); return; } - + // check cache before thinking if (_uniform._buffers[slot] == uniformBuffer) { return; @@ -181,7 +183,7 @@ void GLBackend::do_setUniformBuffer(const Batch& batch, size_t paramOffset) { glBindBufferRange(GL_UNIFORM_BUFFER, slot, object->_buffer, rangeStart, rangeSize); _uniform._buffers[slot] = uniformBuffer; - (void) CHECK_GL_ERROR(); + (void)CHECK_GL_ERROR(); } else { releaseUniformBuffer(slot); return; @@ -195,8 +197,8 @@ void GLBackend::releaseResourceTexture(uint32_t slot) { if (object) { GLuint target = object->_target; glActiveTexture(GL_TEXTURE0 + slot); - glBindTexture(target, 0); // RELEASE - (void) CHECK_GL_ERROR(); + glBindTexture(target, 0); // RELEASE + (void)CHECK_GL_ERROR(); } tex.reset(); } @@ -212,11 +214,11 @@ void GLBackend::resetResourceStage() { } } - void GLBackend::do_setResourceBuffer(const Batch& batch, size_t paramOffset) { GLuint slot = batch._params[paramOffset + 1]._uint; if (slot >= (GLuint)MAX_NUM_RESOURCE_BUFFERS) { - qCDebug(gpugllogging) << "GLBackend::do_setResourceBuffer: Trying to set a resource Buffer at slot #" << slot << " which doesn't exist. MaxNumResourceBuffers = " << getMaxNumResourceBuffers(); + qCDebug(gpugllogging) << "GLBackend::do_setResourceBuffer: Trying to set a resource Buffer at slot #" << slot + << " which doesn't exist. MaxNumResourceBuffers = " << getMaxNumResourceBuffers(); return; } @@ -237,7 +239,7 @@ void GLBackend::do_setResourceBuffer(const Batch& batch, size_t paramOffset) { // If successful bind then cache it if (bindResourceBuffer(slot, resourceBuffer)) { _resource._buffers[slot] = resourceBuffer; - } else { // else clear slot and cache + } else { // else clear slot and cache releaseResourceBuffer(slot); return; } @@ -245,8 +247,9 @@ void GLBackend::do_setResourceBuffer(const Batch& batch, size_t paramOffset) { void GLBackend::do_setResourceTexture(const Batch& batch, size_t paramOffset) { GLuint slot = batch._params[paramOffset + 1]._uint; - if (slot >= (GLuint) MAX_NUM_RESOURCE_TEXTURES) { - qCDebug(gpugllogging) << "GLBackend::do_setResourceTexture: Trying to set a resource Texture at slot #" << slot << " which doesn't exist. MaxNumResourceTextures = " << getMaxNumResourceTextures(); + if (slot >= (GLuint)MAX_NUM_RESOURCE_TEXTURES) { + qCDebug(gpugllogging) << "GLBackend::do_setResourceTexture: Trying to set a resource Texture at slot #" << slot + << " which doesn't exist. MaxNumResourceTextures = " << getMaxNumResourceTextures(); return; } @@ -265,11 +268,14 @@ void GLBackend::bindResourceTexture(uint32_t slot, const TexturePointer& resourc void GLBackend::do_setResourceFramebufferSwapChainTexture(const Batch& batch, size_t paramOffset) { GLuint slot = batch._params[paramOffset + 1]._uint; if (slot >= (GLuint)MAX_NUM_RESOURCE_TEXTURES) { - qCDebug(gpugllogging) << "GLBackend::do_setResourceFramebufferSwapChainTexture: Trying to set a resource Texture at slot #" << slot << " which doesn't exist. MaxNumResourceTextures = " << getMaxNumResourceTextures(); + qCDebug(gpugllogging) + << "GLBackend::do_setResourceFramebufferSwapChainTexture: Trying to set a resource Texture at slot #" << slot + << " which doesn't exist. MaxNumResourceTextures = " << getMaxNumResourceTextures(); return; } - auto swapChain = std::static_pointer_cast(batch._swapChains.get(batch._params[paramOffset + 0]._uint)); + auto swapChain = + std::static_pointer_cast(batch._swapChains.get(batch._params[paramOffset + 0]._uint)); if (!swapChain) { releaseResourceTexture(slot); diff --git a/libraries/gpu-gl-common/src/gpu/gl/GLBackendTransform.cpp b/libraries/gpu-gl-common/src/gpu/gl/GLBackendTransform.cpp index 35d292cd46..ed356acf68 100644 --- a/libraries/gpu-gl-common/src/gpu/gl/GLBackendTransform.cpp +++ b/libraries/gpu-gl-common/src/gpu/gl/GLBackendTransform.cpp @@ -168,7 +168,9 @@ void GLBackend::TransformStageState::update(size_t commandIndex, const StereoSta void GLBackend::TransformStageState::bindCurrentCamera(int eye) const { if (_currentCameraOffset != INVALID_OFFSET) { - glBindBufferRange(GL_UNIFORM_BUFFER, TRANSFORM_CAMERA_SLOT, _cameraBuffer, _currentCameraOffset + eye * _cameraUboSize, sizeof(CameraBufferElement)); + static_assert(TRANSFORM_CAMERA_SLOT >= MAX_NUM_UNIFORM_BUFFERS, "TransformCamera may overlap pipeline uniform buffer slots. Invalidate uniform buffer slot cache for safety (call _uniform._buffers[TRANSFORM_CAMERA_SLOT].reset())."); + glBindBufferRange(GL_UNIFORM_BUFFER, TRANSFORM_CAMERA_SLOT, _cameraBuffer, _currentCameraOffset + eye * _cameraUboSize, + sizeof(CameraBufferElement)); } } diff --git a/libraries/networking/src/DomainHandler.cpp b/libraries/networking/src/DomainHandler.cpp index 871dc26899..39c8b5b1a1 100644 --- a/libraries/networking/src/DomainHandler.cpp +++ b/libraries/networking/src/DomainHandler.cpp @@ -475,13 +475,16 @@ void DomainHandler::processDomainServerConnectionDeniedPacket(QSharedPointer= MAX_SILENT_DOMAIN_SERVER_CHECK_INS) { + if (_checkInPacketsSinceLastReply > MAX_SILENT_DOMAIN_SERVER_CHECK_INS) { // we haven't heard back from DS in MAX_SILENT_DOMAIN_SERVER_CHECK_INS // so emit our signal that says that qCDebug(networking) << "Limit of silent domain checkins reached"; emit limitOfSilentDomainCheckInsReached(); + return true; + } else { + return false; } } diff --git a/libraries/networking/src/DomainHandler.h b/libraries/networking/src/DomainHandler.h index 4d98391104..a428110db6 100644 --- a/libraries/networking/src/DomainHandler.h +++ b/libraries/networking/src/DomainHandler.h @@ -96,7 +96,7 @@ public: void softReset(); int getCheckInPacketsSinceLastReply() const { return _checkInPacketsSinceLastReply; } - void sentCheckInPacket(); + bool checkInPacketTimeout(); void clearPendingCheckins() { _checkInPacketsSinceLastReply = 0; } /**jsdoc diff --git a/libraries/networking/src/NLPacket.cpp b/libraries/networking/src/NLPacket.cpp index f946e97bf4..620e60945b 100644 --- a/libraries/networking/src/NLPacket.cpp +++ b/libraries/networking/src/NLPacket.cpp @@ -199,7 +199,9 @@ void NLPacket::readVersion() { } void NLPacket::readSourceID() { - if (!PacketTypeEnum::getNonSourcedPackets().contains(_type)) { + if (PacketTypeEnum::getNonSourcedPackets().contains(_type)) { + _sourceID = NULL_LOCAL_ID; + } else { _sourceID = sourceIDInHeader(*this); } } diff --git a/libraries/networking/src/NodeList.cpp b/libraries/networking/src/NodeList.cpp index c5c49f68fe..d9d5c21e5d 100644 --- a/libraries/networking/src/NodeList.cpp +++ b/libraries/networking/src/NodeList.cpp @@ -305,7 +305,8 @@ void NodeList::sendDomainServerCheckIn() { } else if (_domainHandler.getIP().isNull() && _domainHandler.requiresICE()) { qCDebug(networking) << "Waiting for ICE discovered domain-server socket. Will not send domain-server check in."; handleICEConnectionToDomainServer(); - } else if (!_domainHandler.getIP().isNull()) { + // let the domain handler know we are due to send a checkin packet + } else if (!_domainHandler.getIP().isNull() && !_domainHandler.checkInPacketTimeout()) { PacketType domainPacketType = !_domainHandler.isConnected() ? PacketType::DomainConnectRequest : PacketType::DomainListRequest; @@ -419,10 +420,15 @@ void NodeList::sendDomainServerCheckIn() { flagTimeForConnectionStep(LimitedNodeList::ConnectionStep::SendDSCheckIn); + // Send duplicate check-ins in the exponentially increasing sequence 1, 1, 2, 4, ... + int outstandingCheckins = _domainHandler.getCheckInPacketsSinceLastReply(); + int checkinCount = outstandingCheckins > 1 ? std::pow(2, outstandingCheckins - 2) : 1; + for (int i = 1; i < checkinCount; ++i) { + auto packetCopy = domainPacket->createCopy(*domainPacket); + sendPacket(std::move(packetCopy), _domainHandler.getSockAddr()); + } sendPacket(std::move(domainPacket), _domainHandler.getSockAddr()); - - // let the domain handler know we sent another check in or connect packet - _domainHandler.sentCheckInPacket(); + } } diff --git a/libraries/octree/src/OctreeProcessor.cpp b/libraries/octree/src/OctreeProcessor.cpp index db78e985e6..beaac1198c 100644 --- a/libraries/octree/src/OctreeProcessor.cpp +++ b/libraries/octree/src/OctreeProcessor.cpp @@ -20,12 +20,6 @@ #include "OctreeLogging.h" -OctreeProcessor::OctreeProcessor() : - _tree(NULL), - _managedTree(false) -{ -} - void OctreeProcessor::init() { if (!_tree) { _tree = createTree(); @@ -34,6 +28,9 @@ void OctreeProcessor::init() { } OctreeProcessor::~OctreeProcessor() { + if (_tree) { + _tree->eraseAllOctreeElements(false); + } } void OctreeProcessor::setTree(OctreePointer newTree) { diff --git a/libraries/octree/src/OctreeProcessor.h b/libraries/octree/src/OctreeProcessor.h index 25e280abca..325b33cd15 100644 --- a/libraries/octree/src/OctreeProcessor.h +++ b/libraries/octree/src/OctreeProcessor.h @@ -28,7 +28,6 @@ class OctreeProcessor : public QObject, public QEnableSharedFromThis { Q_OBJECT public: - OctreeProcessor(); virtual ~OctreeProcessor(); virtual char getMyNodeType() const = 0; @@ -61,7 +60,7 @@ protected: virtual OctreePointer createTree() = 0; OctreePointer _tree; - bool _managedTree; + bool _managedTree { false }; SimpleMovingAverage _elementsPerPacket; SimpleMovingAverage _entitiesPerPacket; diff --git a/libraries/physics/src/CharacterController.cpp b/libraries/physics/src/CharacterController.cpp index 64eda975cf..bb076c89f2 100755 --- a/libraries/physics/src/CharacterController.cpp +++ b/libraries/physics/src/CharacterController.cpp @@ -269,7 +269,8 @@ void CharacterController::playerStep(btCollisionWorld* collisionWorld, btScalar } btQuaternion deltaRot = desiredRot * startRot.inverse(); float angularSpeed = deltaRot.getAngle() / _followTimeRemaining; - btQuaternion angularDisplacement = btQuaternion(deltaRot.getAxis(), angularSpeed * dt); + glm::vec3 rotationAxis = glm::normalize(glm::axis(bulletToGLM(deltaRot))); // deltaRot.getAxis() is inaccurate + btQuaternion angularDisplacement = btQuaternion(glmToBullet(rotationAxis), angularSpeed * dt); btQuaternion endRot = angularDisplacement * startRot; // in order to accumulate displacement of avatar position, we need to take _shapeLocalOffset into account. diff --git a/libraries/physics/src/EntityMotionState.cpp b/libraries/physics/src/EntityMotionState.cpp index e7b9f17739..9089f02aaf 100644 --- a/libraries/physics/src/EntityMotionState.cpp +++ b/libraries/physics/src/EntityMotionState.cpp @@ -834,3 +834,14 @@ void EntityMotionState::clearObjectVelocities() const { } _entity->setAcceleration(glm::vec3(0.0f)); } + +void EntityMotionState::saveKinematicState(btScalar timeStep) { + _body->saveKinematicState(timeStep); + + // This is a WORKAROUND for a quirk in Bullet: due to floating point error slow spinning kinematic objects will + // have a measured angular velocity of zero. This probably isn't a bug that the Bullet team is interested in + // fixing since there is one very simple workaround: use double-precision math for the physics simulation. + // We're not ready migrate to double-precision yet so we explicitly work around it by slamming the RigidBody's + // angular velocity with the value in the entity. + _body->setAngularVelocity(glmToBullet(_entity->getWorldAngularVelocity())); +} diff --git a/libraries/physics/src/EntityMotionState.h b/libraries/physics/src/EntityMotionState.h index c2d4f8d87e..b215537d55 100644 --- a/libraries/physics/src/EntityMotionState.h +++ b/libraries/physics/src/EntityMotionState.h @@ -97,6 +97,7 @@ public: OwnershipState getOwnershipState() const { return _ownershipState; } void setRegion(uint8_t region); + void saveKinematicState(btScalar timeStep) override; protected: void updateSendVelocities(); diff --git a/libraries/physics/src/ObjectMotionState.cpp b/libraries/physics/src/ObjectMotionState.cpp index 161d6bd636..0e6eb2511d 100644 --- a/libraries/physics/src/ObjectMotionState.cpp +++ b/libraries/physics/src/ObjectMotionState.cpp @@ -347,7 +347,7 @@ void ObjectMotionState::updateLastKinematicStep() { } void ObjectMotionState::updateBodyMassProperties() { - float mass = getMass(); + btScalar mass = getMass(); btVector3 inertia(1.0f, 1.0f, 1.0f); if (mass > 0.0f) { _body->getCollisionShape()->calculateLocalInertia(mass, inertia); @@ -356,3 +356,7 @@ void ObjectMotionState::updateBodyMassProperties() { _body->updateInertiaTensor(); } +void ObjectMotionState::saveKinematicState(btScalar timeStep) { + _body->saveKinematicState(timeStep); +} + diff --git a/libraries/physics/src/ObjectMotionState.h b/libraries/physics/src/ObjectMotionState.h index 4a3b200559..7439c1c38d 100644 --- a/libraries/physics/src/ObjectMotionState.h +++ b/libraries/physics/src/ObjectMotionState.h @@ -165,6 +165,7 @@ public: virtual bool isLocallyOwned() const { return false; } virtual bool isLocallyOwnedOrShouldBe() const { return false; } // aka shouldEmitCollisionEvents() + virtual void saveKinematicState(btScalar timeStep); friend class PhysicsEngine; diff --git a/libraries/physics/src/ThreadSafeDynamicsWorld.cpp b/libraries/physics/src/ThreadSafeDynamicsWorld.cpp index 07d5ceb9ac..17a52f7cd9 100644 --- a/libraries/physics/src/ThreadSafeDynamicsWorld.cpp +++ b/libraries/physics/src/ThreadSafeDynamicsWorld.cpp @@ -162,7 +162,13 @@ void ThreadSafeDynamicsWorld::saveKinematicState(btScalar timeStep) { for (int i=0;iisKinematicObject() && body->getActivationState() != ISLAND_SLEEPING) { - body->saveKinematicState(timeStep); + if (body->getMotionState()) { + btMotionState* motionState = body->getMotionState(); + ObjectMotionState* objectMotionState = static_cast(motionState); + objectMotionState->saveKinematicState(timeStep); + } else { + body->saveKinematicState(timeStep); + } } } } diff --git a/libraries/render-utils/src/DeferredGlobalLight.slh b/libraries/render-utils/src/DeferredGlobalLight.slh index c4894200a3..d92fc0dbfd 100644 --- a/libraries/render-utils/src/DeferredGlobalLight.slh +++ b/libraries/render-utils/src/DeferredGlobalLight.slh @@ -198,7 +198,7 @@ vec3 evalGlobalLightingAlphaBlended(mat4 invViewMat, float shadowAttenuation, fl vec3 directionalSpecular; evalLightingDirectional(directionalDiffuse, directionalSpecular, lightDirection, lightIrradiance, surfaceWS, metallic, fresnel, albedo, shadowAttenuation); color += directionalDiffuse; - color += (ambientSpecular + directionalSpecular) / opacity; + color += evalSpecularWithOpacity(ambientSpecular + directionalSpecular, opacity); return color; } @@ -231,7 +231,7 @@ vec3 evalGlobalLightingAlphaBlendedWithHaze( vec3 directionalSpecular; evalLightingDirectional(directionalDiffuse, directionalSpecular, lightDirection, lightIrradiance, surfaceWS, metallic, fresnel, albedo, shadowAttenuation); color += directionalDiffuse; - color += (ambientSpecular + directionalSpecular) / opacity; + color += evalSpecularWithOpacity(ambientSpecular + directionalSpecular, opacity); // Haze if ((isHazeEnabled() > 0.0) && (hazeParams.hazeMode & HAZE_MODE_IS_ACTIVE) == HAZE_MODE_IS_ACTIVE) { @@ -269,7 +269,7 @@ vec3 evalGlobalLightingAlphaBlendedWithHaze( evalLightingDirectional(directionalDiffuse, directionalSpecular, lightDirection, lightIrradiance, surface, metallic, fresnel, albedo, shadowAttenuation); color += ambientDiffuse + directionalDiffuse; - color += (ambientSpecular + directionalSpecular) / opacity; + color += evalSpecularWithOpacity(ambientSpecular + directionalSpecular, opacity); // Haze if ((isHazeEnabled() > 0.0) && (hazeParams.hazeMode & HAZE_MODE_IS_ACTIVE) == HAZE_MODE_IS_ACTIVE) { diff --git a/libraries/render-utils/src/ForwardGlobalLight.slh b/libraries/render-utils/src/ForwardGlobalLight.slh index 84999f347b..eccc44186c 100644 --- a/libraries/render-utils/src/ForwardGlobalLight.slh +++ b/libraries/render-utils/src/ForwardGlobalLight.slh @@ -197,7 +197,7 @@ vec3 evalGlobalLightingAlphaBlended(mat4 invViewMat, float shadowAttenuation, fl vec3 directionalSpecular; evalLightingDirectional(directionalDiffuse, directionalSpecular, lightDirection, lightIrradiance, surfaceWS, metallic, fresnel, albedo, shadowAttenuation); color += directionalDiffuse; - color += (ambientSpecular + directionalSpecular) / opacity; + color += evalSpecularWithOpacity(ambientSpecular + directionalSpecular, opacity); return color; } @@ -223,7 +223,7 @@ vec3 evalGlobalLightingAlphaBlendedWithHaze( vec3 directionalSpecular; evalLightingDirectional(directionalDiffuse, directionalSpecular, lightDirection, lightIrradiance, surfaceWS, metallic, fresnel, albedo, shadowAttenuation); color += directionalDiffuse; - color += (ambientSpecular + directionalSpecular) / opacity; + color += evalSpecularWithOpacity(ambientSpecular + directionalSpecular, opacity); // Haze // FIXME - temporarily removed until we support it for forward... diff --git a/libraries/render-utils/src/LightLocal.slh b/libraries/render-utils/src/LightLocal.slh index 515a065d2e..06f8871e24 100644 --- a/libraries/render-utils/src/LightLocal.slh +++ b/libraries/render-utils/src/LightLocal.slh @@ -143,6 +143,6 @@ vec4 evalLocalLighting(ivec3 cluster, int numLights, vec3 fragWorldPos, SurfaceD fragSpecular *= isSpecularEnabled(); fragColor.rgb += fragDiffuse; - fragColor.rgb += fragSpecular / opacity; + fragColor.rgb += evalSpecularWithOpacity(fragSpecular, opacity); return fragColor; } \ No newline at end of file diff --git a/libraries/render-utils/src/LightingModel.slh b/libraries/render-utils/src/LightingModel.slh index 3b1c94f949..fe2d684c32 100644 --- a/libraries/render-utils/src/LightingModel.slh +++ b/libraries/render-utils/src/LightingModel.slh @@ -314,6 +314,9 @@ void evalFragShadingGloss(out vec3 diffuse, out vec3 specular, specular = shading.xyz; } +vec3 evalSpecularWithOpacity(vec3 specular, float opacity) { + return specular / opacity; +} <@if not GETFRESNEL0@> <@def GETFRESNEL0@> diff --git a/libraries/render-utils/src/MaterialTextures.slh b/libraries/render-utils/src/MaterialTextures.slh index 4bcd74eefe..0b83fd1334 100644 --- a/libraries/render-utils/src/MaterialTextures.slh +++ b/libraries/render-utils/src/MaterialTextures.slh @@ -267,7 +267,7 @@ vec3 fetchLightmapMap(vec2 uv) { <@func discardTransparent(opacity)@> { - if (<$opacity$> < 1.0) { + if (<$opacity$> < 1e-6) { discard; } } diff --git a/libraries/render-utils/src/forward_model_translucent.slf b/libraries/render-utils/src/forward_model_translucent.slf index b8d43f15f1..70a3233737 100644 --- a/libraries/render-utils/src/forward_model_translucent.slf +++ b/libraries/render-utils/src/forward_model_translucent.slf @@ -41,6 +41,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent.slf b/libraries/render-utils/src/model_translucent.slf index 71f76c8a8d..b808ca4bab 100644 --- a/libraries/render-utils/src/model_translucent.slf +++ b/libraries/render-utils/src/model_translucent.slf @@ -44,6 +44,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent_fade.slf b/libraries/render-utils/src/model_translucent_fade.slf index 8b40186448..a93adee96b 100644 --- a/libraries/render-utils/src/model_translucent_fade.slf +++ b/libraries/render-utils/src/model_translucent_fade.slf @@ -46,6 +46,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent_normal_map.slf b/libraries/render-utils/src/model_translucent_normal_map.slf index 320e883bb0..750149dc1b 100644 --- a/libraries/render-utils/src/model_translucent_normal_map.slf +++ b/libraries/render-utils/src/model_translucent_normal_map.slf @@ -45,6 +45,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent_normal_map_fade.slf b/libraries/render-utils/src/model_translucent_normal_map_fade.slf index 0e114f7fdd..c7615626ce 100644 --- a/libraries/render-utils/src/model_translucent_normal_map_fade.slf +++ b/libraries/render-utils/src/model_translucent_normal_map_fade.slf @@ -54,6 +54,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent_unlit.slf b/libraries/render-utils/src/model_translucent_unlit.slf index ebe9901616..e5507dd2e0 100644 --- a/libraries/render-utils/src/model_translucent_unlit.slf +++ b/libraries/render-utils/src/model_translucent_unlit.slf @@ -31,6 +31,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/render-utils/src/model_translucent_unlit_fade.slf b/libraries/render-utils/src/model_translucent_unlit_fade.slf index 0f7c3366bb..016db4639f 100644 --- a/libraries/render-utils/src/model_translucent_unlit_fade.slf +++ b/libraries/render-utils/src/model_translucent_unlit_fade.slf @@ -41,6 +41,7 @@ void main(void) { float opacity = getMaterialOpacity(mat) * _alpha; <$evalMaterialOpacity(albedoTex.a, opacity, matKey, opacity)$>; + <$discardTransparent(opacity)$>; vec3 albedo = getMaterialAlbedo(mat); <$evalMaterialAlbedo(albedoTex, albedo, matKey, albedo)$>; diff --git a/libraries/shared/src/FaceshiftConstants.cpp b/libraries/shared/src/FaceshiftConstants.cpp index e6c929409a..0d6f718e49 100644 --- a/libraries/shared/src/FaceshiftConstants.cpp +++ b/libraries/shared/src/FaceshiftConstants.cpp @@ -64,3 +64,18 @@ const char* FACESHIFT_BLENDSHAPES[] = { }; const int NUM_FACESHIFT_BLENDSHAPES = sizeof(FACESHIFT_BLENDSHAPES) / sizeof(char*); + +const int EYE_BLINK_L_INDEX = 0; +const int EYE_BLINK_R_INDEX = 1; +const int EYE_SQUINT_L_INDEX = 2; +const int EYE_SQUINT_R_INDEX = 3; +const int EYE_OPEN_L_INDEX = 8; +const int EYE_OPEN_R_INDEX = 9; +const int BROWS_U_L_INDEX = 17; +const int BROWS_U_R_INDEX = 18; + + +const int EYE_BLINK_INDICES[] = { EYE_BLINK_L_INDEX, EYE_BLINK_R_INDEX }; +const int EYE_SQUINT_INDICES[] = { EYE_SQUINT_L_INDEX, EYE_SQUINT_R_INDEX }; +const int EYE_OPEN_INDICES[] = { EYE_OPEN_L_INDEX, EYE_OPEN_R_INDEX }; +const int BROWS_U_INDICES[] = { BROWS_U_L_INDEX, BROWS_U_R_INDEX }; diff --git a/libraries/shared/src/FaceshiftConstants.h b/libraries/shared/src/FaceshiftConstants.h index ee6e43fdbc..4349a3a21e 100644 --- a/libraries/shared/src/FaceshiftConstants.h +++ b/libraries/shared/src/FaceshiftConstants.h @@ -16,5 +16,10 @@ extern const char* FACESHIFT_BLENDSHAPES[]; /// The size of FACESHIFT_BLENDSHAPES extern const int NUM_FACESHIFT_BLENDSHAPES; +// Eyes and Brows indices +extern const int EYE_BLINK_INDICES[]; +extern const int EYE_OPEN_INDICES[]; +extern const int BROWS_U_INDICES[]; +extern const int EYE_SQUINT_INDICES[]; -#endif // hifi_FaceshiftConstants_h \ No newline at end of file +#endif // hifi_FaceshiftConstants_h diff --git a/scripts/system/controllers/controllerDisplay.js b/scripts/system/controllers/controllerDisplay.js index dc7c9b37bd..8aa0393357 100644 --- a/scripts/system/controllers/controllerDisplay.js +++ b/scripts/system/controllers/controllerDisplay.js @@ -108,14 +108,13 @@ createControllerDisplay = function(config) { for (var partName in controller.parts) { overlayID = this.overlays[i++]; var part = controller.parts[partName]; - localPosition = Vec3.sum(controller.position, Vec3.multiplyQbyV(controller.rotation, part.naturalPosition)); + localPosition = Vec3.subtract(part.naturalPosition, controller.naturalPosition); var localRotation; var value = this.partValues[partName]; var offset, rotation; if (value !== undefined) { if (part.type === "linear") { - var axis = Vec3.multiplyQbyV(controller.rotation, part.axis); - offset = Vec3.multiply(part.maxTranslation * value, axis); + offset = Vec3.multiply(part.maxTranslation * value, part.axis); localPosition = Vec3.sum(localPosition, offset); localRotation = undefined; } else if (part.type === "joystick") { @@ -126,8 +125,8 @@ createControllerDisplay = function(config) { } else { offset = { x: 0, y: 0, z: 0 }; } - localPosition = Vec3.sum(controller.position, Vec3.multiplyQbyV(controller.rotation, Vec3.sum(offset, part.naturalPosition))); - localRotation = Quat.multiply(controller.rotation, rotation); + localPosition = Vec3.sum(offset, localPosition); + localRotation = rotation; } else if (part.type === "rotational") { value = clamp(value, part.minValue, part.maxValue); var pct = (value - part.minValue) / part.maxValue; @@ -139,8 +138,8 @@ createControllerDisplay = function(config) { } else { offset = { x: 0, y: 0, z: 0 }; } - localPosition = Vec3.sum(controller.position, Vec3.multiplyQbyV(controller.rotation, Vec3.sum(offset, part.naturalPosition))); - localRotation = Quat.multiply(controller.rotation, rotation); + localPosition = Vec3.sum(offset, localPosition); + localRotation = rotation; } } if (localRotation !== undefined) { @@ -169,9 +168,11 @@ createControllerDisplay = function(config) { if (controller.naturalPosition) { position = Vec3.sum(Vec3.multiplyQbyV(controller.rotation, controller.naturalPosition), position); + } else { + controller.naturalPosition = { x: 0, y: 0, z: 0 }; } - var overlayID = Overlays.addOverlay("model", { + var baseOverlayID = Overlays.addOverlay("model", { url: controller.modelURL, dimensions: Vec3.multiply(sensorScaleFactor, controller.dimensions), localRotation: controller.rotation, @@ -181,23 +182,21 @@ createControllerDisplay = function(config) { ignoreRayIntersection: true }); - controllerDisplay.overlays.push(overlayID); - overlayID = null; + controllerDisplay.overlays.push(baseOverlayID); if (controller.parts) { for (var partName in controller.parts) { var part = controller.parts[partName]; - var partPosition = Vec3.sum(controller.position, Vec3.multiplyQbyV(controller.rotation, part.naturalPosition)); - var innerRotation = controller.rotation; + var localPosition = Vec3.subtract(part.naturalPosition, controller.naturalPosition); + var localRotation = { x: 0, y: 0, z: 0, w: 1 } controllerDisplay.parts[partName] = controller.parts[partName]; var properties = { url: part.modelURL, - localPosition: partPosition, - localRotation: innerRotation, - parentID: MyAvatar.SELF_ID, - parentJointIndex: controller.jointIndex, + localPosition: localPosition, + localRotation: localRotation, + parentID: baseOverlayID, ignoreRayIntersection: true }; @@ -207,11 +206,10 @@ createControllerDisplay = function(config) { properties['textures'] = textures; } - overlayID = Overlays.addOverlay("model", properties); + var overlayID = Overlays.addOverlay("model", properties); if (part.type === "rotational") { var input = resolveHardware(part.input); - print("Mapping to: ", part.input, input); mapping.from([input]).peek().to(function(partName) { return function(value) { // insert the most recent controller value into controllerDisplay.partValues. diff --git a/scripts/system/controllers/handTouch.js b/scripts/system/controllers/handTouch.js index c20b86b775..5e633d4740 100644 --- a/scripts/system/controllers/handTouch.js +++ b/scripts/system/controllers/handTouch.js @@ -605,7 +605,6 @@ var finger = fingerKeys[i]; var LOOKUP_DISTANCE_MULTIPLIER = 1.5; var dist = LOOKUP_DISTANCE_MULTIPLIER*data.distance; - console.log("distance: " + dist); var checkOffset = { x: data.perpendicular.x * dist, y: data.perpendicular.y * dist, diff --git a/scripts/system/edit.js b/scripts/system/edit.js index 464ccf2995..5461538046 100644 --- a/scripts/system/edit.js +++ b/scripts/system/edit.js @@ -1835,7 +1835,7 @@ var keyReleaseEvent = function (event) { deleteSelectedEntities(); } else if (event.text === "ESC") { selectionManager.clearSelections(); - } else if (event.text === "TAB") { + } else if (event.text === "t") { selectionDisplay.toggleSpaceMode(); } else if (event.text === "f") { if (isActive) { diff --git a/scripts/system/html/js/SnapshotReview.js b/scripts/system/html/js/SnapshotReview.js index 0c3e6199f3..91866605a4 100644 --- a/scripts/system/html/js/SnapshotReview.js +++ b/scripts/system/html/js/SnapshotReview.js @@ -668,6 +668,7 @@ window.onload = function () { addImage(element, messageOptions.isLoggedIn, idx === 0 && messageOptions.canShare, idx === 1, false, false, false, true); }); document.getElementById("p1").classList.add("processingGif"); + document.getElementById("snap-button").disabled = true; } else { var gifPath = message.image_data[0].localPath, p1img = document.getElementById('p1img'); @@ -677,14 +678,15 @@ window.onload = function () { shareForUrl("p1"); appendShareBar("p1", messageOptions.isLoggedIn, messageOptions.canShare, true, false, false, messageOptions.canBlast); document.getElementById("p1").classList.remove("processingGif"); + document.getElementById("snap-button").disabled = false; } } else { imageCount = message.image_data.length; message.image_data.forEach(function (element) { addImage(element, messageOptions.isLoggedIn, messageOptions.canShare, false, false, false, false, true); }); + document.getElementById("snap-button").disabled = false; } - document.getElementById("snap-button").disabled = false; break; case 'captureSettings': handleCaptureSetting(message.setting); @@ -701,7 +703,7 @@ window.onload = function () { case 'snapshotUploadComplete': var isGif = fileExtensionMatches(message.image_url, "gif"); updateShareInfo(isGif ? "p1" : "p0", message.story_id); - if (isPrintProcessing()) { + if (isPrintProcessing()) { setPrintButtonEnabled(); } break; @@ -724,11 +726,11 @@ function snapshotSettings() { })); } function takeSnapshot() { + document.getElementById("snap-button").disabled = true; EventBridge.emitWebEvent(JSON.stringify({ type: "snapshot", action: "takeSnapshot" })); - document.getElementById("snap-button").disabled = true; } function isPrintDisabled() { @@ -739,14 +741,14 @@ function isPrintDisabled() { document.getElementById('print-button').disabled; } function isPrintProcessing() { - var printElement = document.getElementById('print-icon'); + var printElement = document.getElementById('print-icon'); return printElement.classList.contains("print-icon") && printElement.classList.contains("print-icon-loading") && document.getElementById('print-button').disabled; } function isPrintEnabled() { - var printElement = document.getElementById('print-icon'); + var printElement = document.getElementById('print-icon'); return printElement.classList.contains("print-icon") && printElement.classList.contains("print-icon-default") && @@ -773,8 +775,8 @@ function requestPrintButtonUpdate() { })); } -function printToPolaroid() { - if (isPrintEnabled()) { +function printToPolaroid() { + if (isPrintEnabled()) { EventBridge.emitWebEvent(JSON.stringify({ type: "snapshot", action: "printToPolaroid" diff --git a/scripts/system/libraries/entitySelectionTool.js b/scripts/system/libraries/entitySelectionTool.js index cd3c9fe418..d30de1045f 100644 --- a/scripts/system/libraries/entitySelectionTool.js +++ b/scripts/system/libraries/entitySelectionTool.js @@ -215,8 +215,10 @@ SelectionManager = (function() { that.worldRotation = properties.boundingBox.rotation; that.entityType = properties.type; - - SelectionDisplay.setSpaceMode(SPACE_LOCAL); + + if (selectionUpdated) { + SelectionDisplay.setSpaceMode(SPACE_LOCAL); + } } else { that.localRotation = null; that.localDimensions = null; @@ -1435,7 +1437,7 @@ SelectionDisplay = (function() { that.setHandleRotateYawVisible(!activeTool || isActiveTool(handleRotateYawRing)); that.setHandleRotateRollVisible(!activeTool || isActiveTool(handleRotateRollRing)); - var showScaleStretch = !activeTool && SelectionManager.selections.length === 1; + var showScaleStretch = !activeTool && SelectionManager.selections.length === 1 && spaceMode === SPACE_LOCAL; that.setHandleStretchXVisible(showScaleStretch || isActiveTool(handleStretchXSphere)); that.setHandleStretchYVisible(showScaleStretch || isActiveTool(handleStretchYSphere)); that.setHandleStretchZVisible(showScaleStretch || isActiveTool(handleStretchZSphere)); @@ -2061,7 +2063,7 @@ SelectionDisplay = (function() { }; var onMove = function(event) { - var proportional = (spaceMode === SPACE_WORLD) || directionEnum === STRETCH_DIRECTION.ALL; + var proportional = directionEnum === STRETCH_DIRECTION.ALL; var position, rotation; if (spaceMode === SPACE_LOCAL) { diff --git a/scripts/system/snapshot.js b/scripts/system/snapshot.js index e265ddb621..c4fcb70792 100644 --- a/scripts/system/snapshot.js +++ b/scripts/system/snapshot.js @@ -310,7 +310,7 @@ function printToPolaroid(image_url) { "gravity": { "x": 0, "y": -2.5, "z": 0 }, "velocity": { "x": 0, "y": 1.95, "z": 0 }, - "angularVelocity": { "x": -1.0, "y": 0, "z": -1.3 }, + "angularVelocity": Vec3.multiplyQbyV(MyAvatar.orientation, { "x": -1.0, "y": 0, "z": -1.3 }), "dynamic": true, "collisionsWillMove": true,