From 15665b25e8fc3d751b5bc647862fc0cf46923266 Mon Sep 17 00:00:00 2001 From: Andrew Meadows Date: Fri, 10 Aug 2018 16:05:18 -0700 Subject: [PATCH] give OtherAvatars a proxy in workload --- interface/src/Application.cpp | 4 ++ interface/src/avatar/AvatarManager.cpp | 55 +++++++++++++++++++++----- interface/src/avatar/AvatarManager.h | 9 +++++ interface/src/avatar/OtherAvatar.cpp | 13 ++++++ interface/src/avatar/OtherAvatar.h | 11 ++++++ 5 files changed, 82 insertions(+), 10 deletions(-) diff --git a/interface/src/Application.cpp b/interface/src/Application.cpp index 1d515392b0..c0e024ec1e 100644 --- a/interface/src/Application.cpp +++ b/interface/src/Application.cpp @@ -1094,6 +1094,10 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo // Set File Logger Session UUID auto avatarManager = DependencyManager::get(); auto myAvatar = avatarManager ? avatarManager->getMyAvatar() : nullptr; + if (avatarManager) { + workload::SpacePointer space = getEntities()->getWorkloadSpace(); + avatarManager->setSpace(space); + } auto accountManager = DependencyManager::get(); _logger->setSessionID(accountManager->getSessionID()); diff --git a/interface/src/avatar/AvatarManager.cpp b/interface/src/avatar/AvatarManager.cpp index 0d180bc40d..551847324a 100644 --- a/interface/src/avatar/AvatarManager.cpp +++ b/interface/src/avatar/AvatarManager.cpp @@ -81,6 +81,22 @@ AvatarManager::AvatarManager(QObject* parent) : }); } +AvatarSharedPointer AvatarManager::addAvatar(const QUuid& sessionUUID, const QWeakPointer& mixerWeakPointer) { + AvatarSharedPointer avatar = AvatarHashMap::addAvatar(sessionUUID, mixerWeakPointer); + + const auto otherAvatar = std::static_pointer_cast(avatar); + if (otherAvatar && _space) { + std::unique_lock lock(_spaceLock); + auto spaceIndex = _space->allocateID(); + otherAvatar->setSpaceIndex(spaceIndex); + workload::Sphere sphere(otherAvatar->getWorldPosition(), otherAvatar->getBoundingRadius()); + workload::Transaction transaction; + transaction.reset(spaceIndex, sphere, workload::Owner(otherAvatar)); + _space->enqueueTransaction(transaction); + } + return avatar; +} + AvatarManager::~AvatarManager() { assert(_motionStates.empty()); } @@ -104,6 +120,11 @@ void AvatarManager::init() { } } +void AvatarManager::setSpace(workload::SpacePointer& space ) { + assert(!_space); + _space = space; +} + void AvatarManager::updateMyAvatar(float deltaTime) { bool showWarnings = Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings); PerformanceWarning warn(showWarnings, "AvatarManager::updateMyAvatar()"); @@ -194,18 +215,19 @@ void AvatarManager::updateOtherAvatars(float deltaTime) { int numAVatarsNotUpdated = 0; bool physicsEnabled = qApp->isPhysicsEnabled(); - render::Transaction transaction; + render::Transaction renderTransaction; + workload::Transaction workloadTransaction; while (!sortedAvatars.empty()) { const SortableAvatar& sortData = sortedAvatars.top(); - const auto avatar = std::static_pointer_cast(sortData.getAvatar()); - const auto otherAvatar = std::static_pointer_cast(sortData.getAvatar()); + const auto avatar = std::static_pointer_cast(sortData.getAvatar()); + // TODO: to help us scale to more avatars it would be nice to not have to poll orb state here // if the geometry is loaded then turn off the orb if (avatar->getSkeletonModel()->isLoaded()) { // remove the orb if it is there - otherAvatar->removeOrb(); + avatar->removeOrb(); } else { - otherAvatar->updateOrbPosition(); + avatar->updateOrbPosition(); } bool ignoring = DependencyManager::get()->isPersonalMutingNode(avatar->getID()); @@ -241,15 +263,16 @@ void AvatarManager::updateOtherAvatars(float deltaTime) { numAvatarsUpdated++; } avatar->simulate(deltaTime, inView); - avatar->updateRenderItem(transaction); + avatar->updateRenderItem(renderTransaction); + avatar->updateSpaceProxy(workloadTransaction); avatar->setLastRenderUpdateTime(startTime); } else { // we've spent our full time budget --> bail on the rest of the avatar updates // --> more avatars may freeze until their priority trickles up - // --> some scale or fade animations may glitch + // --> some scale animations may glitch // --> some avatar velocity measurements may be a little off - // no time simulate, but we take the time to count how many were tragically missed + // no time to simulate, but we take the time to count how many were tragically missed bool inView = sortData.getPriority() > OUT_OF_VIEW_THRESHOLD; if (!inView) { break; @@ -275,6 +298,14 @@ void AvatarManager::updateOtherAvatars(float deltaTime) { if (_shouldRender) { qApp->getMain3DScene()->enqueueTransaction(transaction); } + + if (!_spaceProxiesToDelete.empty() && _space) { + std::unique_lock lock(_spaceLock); + workloadTransaction.remove(_spaceProxiesToDelete); + _spaceProxiesToDelete.clear(); + } + _space->enqueueTransaction(workloadTransaction); + _numAvatarsUpdated = numAvatarsUpdated; _numAvatarsNotUpdated = numAVatarsNotUpdated; @@ -363,10 +394,14 @@ AvatarSharedPointer AvatarManager::newSharedAvatar() { } void AvatarManager::handleRemovedAvatar(const AvatarSharedPointer& removedAvatar, KillAvatarReason removalReason) { - AvatarHashMap::handleRemovedAvatar(removedAvatar, removalReason); + auto avatar = std::static_pointer_cast(removedAvatar); + { + std::unique_lock lock(_spaceLock); + _spaceProxiesToDelete.push_back(avatar->getSpaceIndex()); + } + AvatarHashMap::handleRemovedAvatar(avatar, removalReason); // remove from physics - auto avatar = std::static_pointer_cast(removedAvatar); avatar->setPhysicsCallback(nullptr); AvatarMotionStateMap::iterator itr = _motionStates.find(avatar.get()); if (itr != _motionStates.end()) { diff --git a/interface/src/avatar/AvatarManager.h b/interface/src/avatar/AvatarManager.h index ecf9a2d735..316e247aa0 100644 --- a/interface/src/avatar/AvatarManager.h +++ b/interface/src/avatar/AvatarManager.h @@ -23,6 +23,7 @@ #include #include #include +#include #include "AvatarMotionState.h" #include "MyAvatar.h" @@ -62,6 +63,7 @@ public: virtual ~AvatarManager(); void init(); + void setSpace(workload::SpacePointer& space ); std::shared_ptr getMyAvatar() { return _myAvatar; } glm::vec3 getMyAvatarPosition() const { return _myAvatar->getWorldPosition(); } @@ -183,6 +185,9 @@ public slots: */ void updateAvatarRenderStatus(bool shouldRenderAvatars); +protected: + AvatarSharedPointer addAvatar(const QUuid& sessionUUID, const QWeakPointer& mixerWeakPointer) override; + private: explicit AvatarManager(QObject* parent = 0); explicit AvatarManager(const AvatarManager& other); @@ -212,6 +217,10 @@ private: float _avatarSimulationTime { 0.0f }; bool _shouldRender { true }; mutable int _identityRequestsSent { 0 }; + + mutable std::mutex _spaceLock; + workload::SpacePointer _space; + std::vector _spaceProxiesToDelete; }; #endif // hifi_AvatarManager_h diff --git a/interface/src/avatar/OtherAvatar.cpp b/interface/src/avatar/OtherAvatar.cpp index 2061df6004..579301aab1 100644 --- a/interface/src/avatar/OtherAvatar.cpp +++ b/interface/src/avatar/OtherAvatar.cpp @@ -58,3 +58,16 @@ void OtherAvatar::createOrb() { _otherAvatarOrbMeshPlaceholder->setVisible(true); } } + +void OtherAvatar::setSpaceIndex(int32_t index) { + assert(_spaceIndex == -1); + _spaceIndex = index; +} + +void OtherAvatar::updateSpaceProxy(workload::Transaction& transaction) const { + if (_spaceIndex > -1) { + float approximateBoundingRadius = glm::length(getTargetScale()); + workload::Sphere sphere(getWorldPosition(), approximateBoundingRadius); + transaction.update(_spaceIndex, sphere); + } +} diff --git a/interface/src/avatar/OtherAvatar.h b/interface/src/avatar/OtherAvatar.h index f33952b78b..8d32e49579 100644 --- a/interface/src/avatar/OtherAvatar.h +++ b/interface/src/avatar/OtherAvatar.h @@ -14,7 +14,10 @@ #include "ui/overlays/Sphere3DOverlay.h" #include "InterfaceLogging.h" +#include + class OtherAvatar : public Avatar { + Q_OBJECT public: explicit OtherAvatar(QThread* thread); virtual ~OtherAvatar(); @@ -24,9 +27,17 @@ public: void updateOrbPosition(); void removeOrb(); + void setSpaceIndex(int32_t index); + int32_t getSpaceIndex() const { return _spaceIndex; } + void updateSpaceProxy(workload::Transaction& transaction) const; + +signals: + void spaceUpdate(std::pair data); + protected: std::shared_ptr _otherAvatarOrbMeshPlaceholder { nullptr }; OverlayID _otherAvatarOrbMeshPlaceholderID { UNKNOWN_OVERLAY_ID }; + int32_t _spaceIndex { -1 }; }; #endif // hifi_OtherAvatar_h