mirror of
https://github.com/lubosz/overte.git
synced 2025-04-19 12:24:01 +02:00
Fix shape LOD
This commit is contained in:
parent
19701ef333
commit
65896b3b6f
5 changed files with 103 additions and 20 deletions
|
@ -413,7 +413,7 @@ void AvatarManager::buildPhysicsTransaction(PhysicsEngine::Transaction& transact
|
|||
transaction.objectsToRemove.push_back(mState);
|
||||
}
|
||||
}
|
||||
qCDebug(animation) << "Removing " << detailedMotionStates.size() << " detailed motion states from " << avatar->getSessionUUID();
|
||||
qDebug() << "Removing " << detailedMotionStates.size() << " detailed motion states from " << avatar->getSessionUUID();
|
||||
avatar->resetDetailedMotionStates();
|
||||
} else {
|
||||
if (avatar->_motionState == nullptr) {
|
||||
|
@ -427,20 +427,16 @@ void AvatarManager::buildPhysicsTransaction(PhysicsEngine::Transaction& transact
|
|||
transaction.objectsToAdd.push_back(motionState);
|
||||
}
|
||||
}
|
||||
auto& detailedMotionStates = avatar->getDetailedMotionStates();
|
||||
if (detailedMotionStates.size() == 0) {
|
||||
for (int i = 0; i < avatar->getJointCount(); i++) {
|
||||
auto dMotionState = avatar->createDetailedMotionStateForJoint(avatar, i);
|
||||
if (dMotionState) {
|
||||
detailedMotionStates.push_back(dMotionState);
|
||||
transaction.objectsToAdd.push_back(dMotionState);
|
||||
}
|
||||
if (avatar->getDetailedMotionStates().size() == 0) {
|
||||
avatar->createDetailedMotionStates(avatar);
|
||||
for (auto dMotionState : avatar->getDetailedMotionStates()) {
|
||||
transaction.objectsToAdd.push_back(dMotionState);
|
||||
}
|
||||
if (avatar->_motionState == nullptr || avatar->getDetailedMotionStates().size() == 0) {
|
||||
failedShapeBuilds.insert(avatar);
|
||||
}
|
||||
//qCDebug(animation) << "Creating " << detailedMotionStates.size() << " detailed motion states from " << avatar->getSessionUUID();
|
||||
}
|
||||
if (avatar->_motionState == nullptr || detailedMotionStates.size() == 0) {
|
||||
failedShapeBuilds.insert(avatar);
|
||||
}
|
||||
qDebug() << "Adding " << avatar->getDetailedMotionStates().size() << " detailed motion states from " << avatar->getSessionUUID();
|
||||
}
|
||||
} else if (isInPhysics) {
|
||||
transaction.objectsToChange.push_back(avatar->_motionState);
|
||||
|
@ -450,7 +446,6 @@ void AvatarManager::buildPhysicsTransaction(PhysicsEngine::Transaction& transact
|
|||
transaction.objectsToChange.push_back(mState);
|
||||
}
|
||||
}
|
||||
//qCDebug(animation) << "Updating " << detailedMotionStates.size() << " detailed motion states from " << avatar->getSessionUUID();
|
||||
}
|
||||
}
|
||||
_avatarsToChangeInPhysics.swap(failedShapeBuilds);
|
||||
|
|
|
@ -60,7 +60,13 @@ const btCollisionShape* DetailedMotionState::computeNewShape() {
|
|||
btCollisionShape* shape = nullptr;
|
||||
if (!_avatar->isMyAvatar()) {
|
||||
OtherAvatarPointer otherAvatar = std::static_pointer_cast<OtherAvatar>(_avatar);
|
||||
shape = otherAvatar->createDetailedCollisionShapeForJoint(_jointIndex);
|
||||
if (otherAvatar) {
|
||||
if (_isAvatarCapsule) {
|
||||
shape = otherAvatar->createCapsuleCollisionShape();
|
||||
} else {
|
||||
shape = otherAvatar->createDetailedCollisionShapeForJoint(_jointIndex);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
std::shared_ptr<MyAvatar> myAvatar = std::static_pointer_cast<MyAvatar>(_avatar);
|
||||
shape = myAvatar->getCharacterController()->createDetailedCollisionShapeForJoint(_jointIndex);
|
||||
|
@ -109,7 +115,7 @@ float DetailedMotionState::getObjectAngularDamping() const {
|
|||
|
||||
// virtual
|
||||
glm::vec3 DetailedMotionState::getObjectPosition() const {
|
||||
return _avatar->getJointPosition(_jointIndex);
|
||||
return _isAvatarCapsule ? _avatar->getFitBounds().calcCenter() : _avatar->getJointPosition(_jointIndex);
|
||||
}
|
||||
|
||||
// virtual
|
||||
|
|
|
@ -70,6 +70,7 @@ public:
|
|||
void forceActive();
|
||||
QUuid getAvatarID() { return _avatar->getID(); }
|
||||
int getJointIndex() { return _jointIndex; }
|
||||
void setIsAvatarCapsule(bool isAvatarCapsule) { _isAvatarCapsule = isAvatarCapsule; }
|
||||
|
||||
friend class AvatarManager;
|
||||
friend class Avatar;
|
||||
|
@ -90,6 +91,8 @@ protected:
|
|||
|
||||
uint32_t _dirtyFlags;
|
||||
int _jointIndex { -1 };
|
||||
|
||||
bool _isAvatarCapsule { false };
|
||||
};
|
||||
|
||||
#endif // hifi_DetailedMotionState_h
|
||||
|
|
|
@ -122,6 +122,17 @@ btCollisionShape* OtherAvatar::createDetailedCollisionShapeForJoint(int jointInd
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
btCollisionShape* OtherAvatar::createCapsuleCollisionShape() {
|
||||
ShapeInfo shapeInfo;
|
||||
computeShapeInfo(shapeInfo);
|
||||
shapeInfo.setOffset(glm::vec3(0.0f));
|
||||
if (shapeInfo.getType() != SHAPE_TYPE_NONE) {
|
||||
btCollisionShape* shape = const_cast<btCollisionShape*>(ObjectMotionState::getShapeManager()->getShape(shapeInfo));
|
||||
return shape;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
DetailedMotionState* OtherAvatar::createDetailedMotionStateForJoint(std::shared_ptr<OtherAvatar> avatar, int jointIndex) {
|
||||
auto shape = createDetailedCollisionShapeForJoint(jointIndex);
|
||||
if (shape) {
|
||||
|
@ -132,6 +143,17 @@ DetailedMotionState* OtherAvatar::createDetailedMotionStateForJoint(std::shared_
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
DetailedMotionState* OtherAvatar::createCapsuleMotionState(std::shared_ptr<OtherAvatar> avatar) {
|
||||
auto shape = createCapsuleCollisionShape();
|
||||
if (shape) {
|
||||
DetailedMotionState* motionState = new DetailedMotionState(avatar, shape, -1);
|
||||
motionState->setIsAvatarCapsule(true);
|
||||
motionState->setMass(computeMass());
|
||||
return motionState;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void OtherAvatar::resetDetailedMotionStates() {
|
||||
for (size_t i = 0; i < _detailedMotionStates.size(); i++) {
|
||||
_detailedMotionStates[i] = nullptr;
|
||||
|
@ -141,15 +163,42 @@ void OtherAvatar::resetDetailedMotionStates() {
|
|||
|
||||
void OtherAvatar::setWorkloadRegion(uint8_t region) {
|
||||
_workloadRegion = region;
|
||||
QString printRegion = "";
|
||||
if (region == workload::Region::R1) {
|
||||
printRegion = "R1";
|
||||
} else if (region == workload::Region::R2) {
|
||||
printRegion = "R2";
|
||||
} else if (region == workload::Region::R3) {
|
||||
printRegion = "R3";
|
||||
} else {
|
||||
printRegion = "invalid";
|
||||
}
|
||||
qDebug() << "Setting workload region to " << printRegion;
|
||||
computeShapeLOD();
|
||||
}
|
||||
|
||||
void OtherAvatar::computeShapeLOD() {
|
||||
auto newBodyLOD = (_workloadRegion < workload::Region::R3 && !isDead()) ? BodyLOD::MultiSphereShapes : BodyLOD::CapsuleShape;
|
||||
if (newBodyLOD != _bodyLOD) {
|
||||
_bodyLOD = newBodyLOD;
|
||||
if (isInPhysicsSimulation()) {
|
||||
qDebug() << "Changing to body LOD " << (_bodyLOD == BodyLOD::MultiSphereShapes ? "MultiSpheres" : "Capsule");
|
||||
_needsReinsertion = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool OtherAvatar::isInPhysicsSimulation() const {
|
||||
return _motionState != nullptr && _detailedMotionStates.size() > 0;
|
||||
}
|
||||
|
||||
bool OtherAvatar::shouldBeInPhysicsSimulation() const {
|
||||
return (_workloadRegion < workload::Region::R3 && !isDead());
|
||||
return !(isInPhysicsSimulation() && _needsReinsertion);
|
||||
}
|
||||
|
||||
bool OtherAvatar::needsPhysicsUpdate() const {
|
||||
constexpr uint32_t FLAGS_OF_INTEREST = Simulation::DIRTY_SHAPE | Simulation::DIRTY_MASS | Simulation::DIRTY_POSITION | Simulation::DIRTY_COLLISION_GROUP;
|
||||
return (_motionState && (bool)(_motionState->getIncomingDirtyFlags() & FLAGS_OF_INTEREST));
|
||||
return (_needsReinsertion || _motionState && (bool)(_motionState->getIncomingDirtyFlags() & FLAGS_OF_INTEREST));
|
||||
}
|
||||
|
||||
void OtherAvatar::rebuildCollisionShape() {
|
||||
|
@ -175,4 +224,22 @@ void OtherAvatar::updateCollisionGroup(bool myAvatarCollide) {
|
|||
_motionState->addDirtyFlags(Simulation::DIRTY_COLLISION_GROUP);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void OtherAvatar::createDetailedMotionStates(const std::shared_ptr<OtherAvatar>& avatar){
|
||||
auto& detailedMotionStates = getDetailedMotionStates();
|
||||
if (_bodyLOD == BodyLOD::MultiSphereShapes) {
|
||||
for (int i = 0; i < getJointCount(); i++) {
|
||||
auto dMotionState = createDetailedMotionStateForJoint(avatar, i);
|
||||
if (dMotionState) {
|
||||
detailedMotionStates.push_back(dMotionState);
|
||||
}
|
||||
}
|
||||
} else if (_bodyLOD == BodyLOD::CapsuleShape) {
|
||||
auto dMotionState = createCapsuleMotionState(avatar);
|
||||
if (dMotionState) {
|
||||
detailedMotionStates.push_back(dMotionState);
|
||||
}
|
||||
}
|
||||
_needsReinsertion = false;
|
||||
}
|
||||
|
|
|
@ -27,6 +27,11 @@ public:
|
|||
explicit OtherAvatar(QThread* thread);
|
||||
virtual ~OtherAvatar();
|
||||
|
||||
enum BodyLOD {
|
||||
CapsuleShape,
|
||||
MultiSphereShapes
|
||||
};
|
||||
|
||||
virtual void instantiableAvatar() override { };
|
||||
virtual void createOrb() override;
|
||||
virtual void indicateLoadingStatus(LoadingStatus loadingStatus) override;
|
||||
|
@ -39,7 +44,7 @@ public:
|
|||
|
||||
int parseDataFromBuffer(const QByteArray& buffer) override;
|
||||
|
||||
bool isInPhysicsSimulation() const { return _motionState != nullptr && _detailedMotionStates.size() > 0; }
|
||||
bool isInPhysicsSimulation() const;
|
||||
void rebuildCollisionShape() override;
|
||||
|
||||
void setWorkloadRegion(uint8_t region);
|
||||
|
@ -47,9 +52,14 @@ public:
|
|||
bool needsPhysicsUpdate() const;
|
||||
|
||||
btCollisionShape* createDetailedCollisionShapeForJoint(int jointIndex);
|
||||
btCollisionShape* createCapsuleCollisionShape();
|
||||
DetailedMotionState* createDetailedMotionStateForJoint(std::shared_ptr<OtherAvatar> avatar, int jointIndex);
|
||||
DetailedMotionState* createCapsuleMotionState(std::shared_ptr<OtherAvatar> avatar);
|
||||
void createDetailedMotionStates(const std::shared_ptr<OtherAvatar>& avatar);
|
||||
std::vector<DetailedMotionState*>& getDetailedMotionStates() { return _detailedMotionStates; }
|
||||
void resetDetailedMotionStates();
|
||||
BodyLOD getBodyLOD() { return _bodyLOD; }
|
||||
void computeShapeLOD();
|
||||
|
||||
void updateCollisionGroup(bool myAvatarCollide);
|
||||
|
||||
|
@ -62,6 +72,8 @@ protected:
|
|||
std::vector<DetailedMotionState*> _detailedMotionStates;
|
||||
int32_t _spaceIndex { -1 };
|
||||
uint8_t _workloadRegion { workload::Region::INVALID };
|
||||
BodyLOD _bodyLOD { BodyLOD::CapsuleShape };
|
||||
bool _needsReinsertion { false };
|
||||
};
|
||||
|
||||
using OtherAvatarPointer = std::shared_ptr<OtherAvatar>;
|
||||
|
|
Loading…
Reference in a new issue