16 #include <glm/glm.hpp>
17 #include <glm/gtc/quaternion.hpp>
22 #include <QtCore/QUuid>
24 #include <AvatarData.h>
25 #include <ShapeInfo.h>
26 #include <render/Scene.h>
27 #include <graphics-scripting/Forward.h>
28 #include <GLMHelpers.h>
29 #include <EntityItem.h>
32 #include <ThreadSafeValueCache.h>
35 #include "SkeletonModel.h"
38 #include "MetaModelPayload.h"
39 #include "MultiSphereShape.h"
42 template <>
const ItemKey payloadGetKey(
const AvatarSharedPointer& avatar);
43 template <>
const Item::Bound payloadGetBound(
const AvatarSharedPointer& avatar, RenderArgs* args);
44 template <>
void payloadRender(
const AvatarSharedPointer& avatar, RenderArgs* args);
45 template <> uint32_t metaFetchMetaSubItems(
const AvatarSharedPointer& avatar, ItemIDs& subItems);
46 template <> FadeProperties payloadGetFadeProperties(
const AvatarSharedPointer& avatar,
const TransitionType type);
49 static const float SCALING_RATIO = .05f;
51 extern const float CHAT_MESSAGE_SCALE;
52 extern const float CHAT_MESSAGE_HEIGHT;
54 enum ScreenTintLayer {
55 SCREEN_TINT_BEFORE_LANDSCAPE = 0,
56 SCREEN_TINT_BEFORE_AVATARS,
57 SCREEN_TINT_BEFORE_MY_AVATAR,
58 SCREEN_TINT_AFTER_AVATARS,
59 NUM_SCREEN_TINT_LAYERS
85 struct TransitConfig {
87 int _totalFrames { 0 };
88 float _framesPerMeter { 0.0f };
89 bool _isDistanceBased {
false };
90 float _minTriggerDistance { 0.0f };
91 float _maxTriggerDistance { 0.0f };
92 float _abortDistance{ 0.0f };
93 EaseType _easeType { EaseType::EASE_OUT };
97 Status update(
float deltaTime,
const glm::vec3& avatarPosition,
const TransitConfig& config);
98 void slamPosition(
const glm::vec3& avatarPosition);
99 Status getStatus() {
return _status; }
100 bool isActive() {
return _isActive; }
101 glm::vec3 getCurrentPosition() {
return _currentPosition; }
102 glm::vec3 getEndPosition() {
return _endPosition; }
103 void setScale(
float scale) { _scale = scale; }
107 Status updatePosition(
float deltaTime);
108 void start(
float deltaTime,
const glm::vec3& startPosition,
const glm::vec3& endPosition,
const TransitConfig& config);
109 float getEaseValue(AvatarTransit::EaseType type,
float value);
110 bool _isActive {
false };
112 glm::vec3 _startPosition;
113 glm::vec3 _endPosition;
114 glm::vec3 _currentPosition;
116 glm::vec3 _lastPosition;
118 glm::vec3 _transitLine;
119 float _totalDistance { 0.0f };
120 float _preTransitTime { 0.0f };
121 float _totalTime { 0.0f };
122 float _transitTime { 0.0f };
123 float _postTransitTime { 0.0f };
124 float _currentTime { 0.0f };
125 EaseType _easeType { EaseType::EASE_OUT };
126 Status _status { Status::IDLE };
127 float _scale { 1.0f };
130 class Avatar :
public AvatarData,
public scriptable::ModelProvider,
public MetaModelPayload {
139 Q_PROPERTY(glm::vec3 skeletonOffset READ getSkeletonOffset WRITE setSkeletonOffset)
142 static void setShowAvatars(
bool render);
143 static void setShowReceiveStats(
bool receiveStats);
144 static void setShowMyLookAtVectors(
bool showMine);
145 static void setShowMyLookAtTarget(
bool showMine);
146 static void setShowOtherLookAtVectors(
bool showOthers);
147 static void setShowOtherLookAtTarget(
bool showOthers);
148 static void setShowCollisionShapes(
bool render);
149 static void setShowNamesAboveHeads(
bool show);
151 explicit Avatar(QThread* thread);
154 virtual void instantiableAvatar() = 0;
156 typedef render::Payload<AvatarData> Payload;
159 void removeAvatarEntitiesFromTree();
160 virtual void simulate(
float deltaTime,
bool inView) = 0;
162 virtual void render(RenderArgs* renderArgs);
164 void addToScene(AvatarSharedPointer
self,
const render::ScenePointer& scene,
165 render::Transaction& transaction);
167 void removeFromScene(AvatarSharedPointer
self,
const render::ScenePointer& scene,
168 render::Transaction& transaction);
170 void updateRenderItem(render::Transaction& transaction);
172 virtual void postUpdate(
float deltaTime,
const render::ScenePointer& scene);
175 bool isInitialized()
const {
return _initialized; }
176 SkeletonModelPointer getSkeletonModel() {
return _skeletonModel; }
177 const SkeletonModelPointer getSkeletonModel()
const {
return _skeletonModel; }
178 glm::vec3 getChestPosition()
const;
179 const Head* getHead()
const {
return static_cast<const Head*
>(_headData); }
180 Head* getHead() {
return static_cast<Head*
>(_headData); }
182 AABox getBounds()
const;
185 float getLODDistance()
const;
187 virtual void createOrb() { }
189 enum class LoadingStatus {
195 virtual void indicateLoadingStatus(LoadingStatus loadingStatus) { _loadingStatus = loadingStatus; }
197 virtual QVector<glm::quat> getJointRotations()
const override;
198 using AvatarData::getJointRotation;
199 virtual glm::quat getJointRotation(
int index)
const override;
200 virtual QVector<glm::vec3> getJointTranslations()
const override;
201 using AvatarData::getJointTranslation;
202 virtual glm::vec3 getJointTranslation(
int index)
const override;
203 virtual int getJointIndex(
const QString& name)
const override;
204 virtual QStringList getJointNames()
const override;
206 std::vector<AvatarSkeletonTrait::UnpackedJointData> getSkeletonDefaultData();
216 Q_INVOKABLE
virtual glm::quat getDefaultJointRotation(
int index)
const;
228 Q_INVOKABLE
virtual glm::vec3 getDefaultJointTranslation(
int index)
const;
242 Q_INVOKABLE
virtual glm::quat getAbsoluteDefaultJointRotationInObjectFrame(
int index)
const;
256 Q_INVOKABLE
virtual glm::vec3 getAbsoluteDefaultJointTranslationInObjectFrame(
int index)
const;
259 virtual glm::vec3 getAbsoluteJointScaleInObjectFrame(
int index)
const override;
260 virtual glm::quat getAbsoluteJointRotationInObjectFrame(
int index)
const override;
261 virtual glm::vec3 getAbsoluteJointTranslationInObjectFrame(
int index)
const override;
271 virtual bool setAbsoluteJointRotationInObjectFrame(
int index,
const glm::quat& rotation)
override {
return false; }
281 virtual bool setAbsoluteJointTranslationInObjectFrame(
int index,
const glm::vec3& translation)
override {
return false; }
282 virtual glm::vec3 getSpine2SplineOffset()
const {
return _spine2SplineOffset; }
283 virtual float getSpine2SplineRatio()
const {
return _spine2SplineRatio; }
294 Q_INVOKABLE glm::vec3 worldToJointPoint(
const glm::vec3& position,
const int jointIndex = -1)
const;
304 Q_INVOKABLE glm::vec3 worldToJointDirection(
const glm::vec3& direction,
const int jointIndex = -1)
const;
314 Q_INVOKABLE glm::quat worldToJointRotation(
const glm::quat& rotation,
const int jointIndex = -1)
const;
324 Q_INVOKABLE glm::vec3 jointToWorldPoint(
const glm::vec3& position,
const int jointIndex = -1)
const;
334 Q_INVOKABLE glm::vec3 jointToWorldDirection(
const glm::vec3& direction,
const int jointIndex = -1)
const;
344 Q_INVOKABLE glm::quat jointToWorldRotation(
const glm::quat& rotation,
const int jointIndex = -1)
const;
346 Q_INVOKABLE
virtual void setSkeletonModelURL(
const QUrl& skeletonModelURL)
override;
348 void updateDisplayNameAlpha(
bool showDisplayName);
349 virtual void setSessionDisplayName(
const QString& sessionDisplayName)
override { };
351 virtual int parseDataFromBuffer(
const QByteArray& buffer)
override;
367 Q_INVOKABLE
void setSkeletonOffset(
const glm::vec3& offset);
377 Q_INVOKABLE glm::vec3 getSkeletonOffset() {
return _skeletonOffset; }
379 virtual glm::vec3 getSkeletonPosition()
const;
387 Q_INVOKABLE glm::vec3 getJointPosition(
int index)
const;
397 Q_INVOKABLE glm::vec3 getJointPosition(
const QString& name)
const;
406 Q_INVOKABLE glm::vec3 getNeckPosition()
const;
413 Q_INVOKABLE glm::vec3 getAcceleration()
const {
return _acceleration; }
417 void scaleVectorRelativeToPosition(glm::vec3& positionToScale)
const;
419 void slamPosition(
const glm::vec3& position);
420 virtual void updateAttitude(
const glm::quat& orientation)
override;
425 void applyPositionDelta(
const glm::vec3& delta);
427 virtual void rebuildCollisionShape() = 0;
429 virtual void computeShapeInfo(ShapeInfo& shapeInfo);
430 virtual void computeDetailedShapeInfo(ShapeInfo& shapeInfo,
int jointIndex);
432 void getCapsule(glm::vec3& start, glm::vec3& end,
float& radius);
439 Q_INVOKABLE glm::vec3 getWorldFeetPosition();
441 void setPositionViaScript(
const glm::vec3& position)
override;
442 void setOrientationViaScript(
const glm::quat& orientation)
override;
450 Q_INVOKABLE
virtual const QUuid getParentID()
const override {
return SpatiallyNestable::getParentID(); }
459 Q_INVOKABLE
virtual void setParentID(
const QUuid& parentID)
override;
468 Q_INVOKABLE
virtual quint16 getParentJointIndex()
const override {
return SpatiallyNestable::getParentJointIndex(); }
478 Q_INVOKABLE
virtual void setParentJointIndex(quint16 parentJointIndex)
override;
485 Q_INVOKABLE QList<QVariant> getSkeleton();
488 glm::vec3 getUncachedLeftPalmPosition()
const;
489 glm::quat getUncachedLeftPalmRotation()
const;
490 glm::vec3 getUncachedRightPalmPosition()
const;
491 glm::quat getUncachedRightPalmRotation()
const;
493 uint64_t getLastRenderUpdateTime()
const {
return _lastRenderUpdateTime; }
494 void setLastRenderUpdateTime(uint64_t time) { _lastRenderUpdateTime = time; }
496 void animateScaleChanges(
float deltaTime);
497 void setTargetScale(
float targetScale)
override;
498 float getTargetScale()
const {
return _targetScale; }
506 Q_INVOKABLE
float getSimulationRate(
const QString& rateName = QString(
""))
const;
508 bool hasNewJointData()
const {
return _hasNewJointData; }
510 float getBoundingRadius()
const;
511 AABox getRenderBounds()
const;
512 AABox getFitBounds()
const {
return _fitBoundingBox; }
514 void addToScene(AvatarSharedPointer
self,
const render::ScenePointer& scene);
515 void ensureInScene(AvatarSharedPointer
self,
const render::ScenePointer& scene);
516 bool isInScene()
const {
return render::Item::isValidID(_renderItemID); }
517 render::ItemID getRenderItemID() {
return _renderItemID; }
518 bool isMoving()
const {
return _moving; }
520 void fadeIn(render::ScenePointer scene);
521 void fadeOut(render::Transaction& transaction, KillAvatarReason reason);
522 TransitionType getLastFadeRequested()
const;
523 FadeProperties getFadeProperties(
const TransitionType type)
const;
526 Q_INVOKABLE
virtual float getEyeHeight()
const override;
530 virtual float getUnscaledEyeHeight()
const override;
534 virtual bool canMeasureEyeHeight()
const override {
return true; }
536 virtual float getModelScale()
const {
return _modelScale; }
537 virtual void setModelScale(
float scale) { _modelScale = scale; }
538 virtual glm::vec3 scaleForChildren()
const override {
return glm::vec3(getModelScale()); }
541 virtual void setEnableMeshVisible(
bool isEnabled);
542 virtual bool getEnableMeshVisible()
const;
544 void addMaterial(graphics::MaterialLayer material,
const std::string& parentMaterialName);
545 void removeMaterial(graphics::MaterialPointer material,
const std::string& parentMaterialName);
547 virtual scriptable::ScriptableModelBase getScriptableModel()
override;
549 std::shared_ptr<AvatarTransit> getTransit() {
return std::make_shared<AvatarTransit>(_transit); };
550 AvatarTransit::Status updateTransit(
float deltaTime,
const glm::vec3& avatarPosition,
float avatarScale,
const AvatarTransit::TransitConfig& config);
552 void accumulateGrabPositions(std::map<QUuid, GrabLocationAccumulator>& grabAccumulators);
554 const std::vector<MultiSphereShape>& getMultiSphereShapes()
const {
return _multiSphereShapes; }
555 void tearDownGrabs();
557 uint32_t appendSubMetaItems(render::ItemIDs& subItems);
559 virtual bool shouldRender()
const {
return _isMeshVisible && _isReadyToDraw; }
561 static const float MYAVATAR_ENTITY_LOADING_PRIORITY;
562 static const float OTHERAVATAR_ENTITY_LOADING_PRIORITY;
572 void targetScaleChanged(
float targetScale);
586 glm::vec3 getLeftPalmPosition()
const;
595 glm::quat getLeftPalmRotation()
const;
604 glm::vec3 getRightPalmPosition()
const;
613 glm::quat getRightPalmRotation()
const;
621 void setModelURLFinished(
bool success);
638 float getUnscaledEyeHeightFromSkeleton()
const;
639 void buildUnscaledEyeHeightCache();
640 void buildSpine2SplineRatioCache();
641 void clearUnscaledEyeHeightCache();
642 void clearSpine2SplineRatioCache();
643 virtual const QString& getSessionDisplayNameForTransport()
const override {
return _empty; }
645 virtual void maybeUpdateSessionDisplayNameFromTransport(
const QString& sessionDisplayName)
override { _sessionDisplayName = sessionDisplayName; }
646 void computeMultiSphereShapes();
647 void updateFitBoundingBox();
649 SkeletonModelPointer _skeletonModel;
651 void invalidateJointIndicesCache()
const;
652 void withValidJointIndicesCache(std::function<
void()>
const& worker)
const;
653 mutable QHash<QString, int> _modelJointIndicesCache;
654 mutable QReadWriteLock _modelJointIndicesCacheLock;
655 mutable bool _modelJointsCached {
false };
657 glm::vec3 _skeletonOffset;
659 float _bodyYawDelta { 0.0f };
660 float _seatedBodyYawDelta{ 0.0f };
668 glm::vec3 _positionDeltaAccumulator;
669 glm::vec3 _lastVelocity;
670 glm::vec3 _acceleration;
671 glm::vec3 _angularVelocity;
672 glm::vec3 _lastAngularVelocity;
673 glm::vec3 _angularAcceleration;
674 glm::quat _lastOrientation;
675 glm::vec3 _worldUpDirection { Vectors::UP };
676 bool _moving {
false };
679 bool isLookingAtMe(AvatarSharedPointer avatar)
const;
680 virtual void sendPacket(
const QUuid& entityID)
const { }
681 bool applyGrabChanges();
682 void relayJointDataToChildren();
684 void fade(render::Transaction& transaction, TransitionType type);
686 glm::vec3 getBodyRightDirection()
const {
return getWorldOrientation() * IDENTITY_RIGHT; }
687 glm::vec3 getBodyUpDirection()
const {
return getWorldOrientation() * IDENTITY_UP; }
688 void measureMotionDerivatives(
float deltaTime);
689 bool getCollideWithOtherAvatars()
const {
return _collideWithOtherAvatars; }
691 float getSkeletonHeight()
const;
692 float getHeadHeight()
const;
693 float getPelvisFloatingHeight()
const;
694 glm::vec3 getDisplayNamePosition()
const;
696 Transform calculateDisplayNameTransform(
const ViewFrustum& view,
const glm::vec3& textPosition)
const;
697 void renderDisplayName(gpu::Batch& batch,
const ViewFrustum& view,
const glm::vec3& textPosition,
bool forward)
const;
698 virtual bool shouldRenderHead(
const RenderArgs* renderArgs)
const;
699 virtual void fixupModelsInScene(
const render::ScenePointer& scene);
701 virtual void updatePalms();
703 render::ItemID _renderItemID{ render::Item::INVALID_ITEM_ID };
704 TransitionType _lastFadeRequested { TransitionType::NONE };
706 ThreadSafeValueCache<glm::vec3> _leftPalmPositionCache { glm::vec3() };
707 ThreadSafeValueCache<glm::quat> _leftPalmRotationCache { glm::quat() };
708 ThreadSafeValueCache<glm::vec3> _rightPalmPositionCache { glm::vec3() };
709 ThreadSafeValueCache<glm::quat> _rightPalmRotationCache { glm::quat() };
712 RateCounter<> _simulationRate;
713 RateCounter<> _simulationInViewRate;
714 RateCounter<> _skeletonModelSimulationRate;
715 RateCounter<> _jointDataSimulationRate;
717 class AvatarEntityDataHash {
719 AvatarEntityDataHash(uint32_t h) : hash(h) {};
721 bool success {
false };
724 uint64_t _lastRenderUpdateTime { 0 };
725 int _leftPointerGeometryID { 0 };
726 int _rightPointerGeometryID { 0 };
727 int _nameRectGeometryID { 0 };
728 bool _initialized {
false };
729 bool _isAnimatingScale {
false };
730 bool _mustFadeIn {
false };
731 bool _reconstructSoftEntitiesJointMap {
false };
732 float _modelScale { 1.0f };
734 AvatarTransit _transit;
735 std::mutex _transitLock;
739 float _displayNameTargetAlpha { 1.0f };
740 float _displayNameAlpha { 1.0f };
742 ThreadSafeValueCache<float> _unscaledEyeHeightCache { DEFAULT_AVATAR_EYE_HEIGHT };
743 float _spine2SplineRatio { DEFAULT_SPINE2_SPLINE_PROPORTION };
744 glm::vec3 _spine2SplineOffset;
746 std::unordered_map<std::string, graphics::MultiMaterial> _materials;
747 std::mutex _materialsLock;
749 void processMaterials();
752 bool _isMeshVisible {
true };
753 bool _needMeshVisibleSwitch {
true };
754 bool _isReadyToDraw {
false };
755 bool _needsWearablesLoadedCheck {
false };
756 bool _hasCheckedForAvatarEntities {
false };
758 static const float MYAVATAR_LOADING_PRIORITY;
759 static const float OTHERAVATAR_LOADING_PRIORITY;
761 LoadingStatus _loadingStatus { LoadingStatus::NoModel };
763 static void metaBlendshapeOperator(render::ItemID renderItemID,
int blendshapeNumber,
const QVector<BlendshapeOffset>& blendshapeOffsets,
764 const QVector<int>& blendedMeshSizes,
const render::ItemIDs& subItemIDs);
766 std::vector<MultiSphereShape> _multiSphereShapes;
767 AABox _fitBoundingBox;
768 void clearAvatarGrabData(
const QUuid& grabID)
override;
770 using SetOfIDs = std::set<QUuid>;
771 using VectorOfIDs = std::vector<QUuid>;
772 using MapOfGrabs = std::map<QUuid, GrabPointer>;
774 MapOfGrabs _avatarGrabs;
775 SetOfIDs _grabsToChange;
776 VectorOfIDs _grabsToDelete;
778 ReadWriteLockable _subItemLock;
779 void updateDescendantRenderIDs();
780 render::ItemIDs _descendantRenderIDs;
781 std::unordered_set<EntityItemID> _renderingDescendantEntityIDs;
A simple object wrapper for an OpenGL texture.
Definition: material-networking/src/material-networking/TextureCache.h:39