void MyCharacterController::setAvatarPositionAndOrientation( const glm::vec3& position, const glm::quat& orientation) { // TODO: update gravity if up has changed updateUpAxis(orientation); btQuaternion bodyOrientation = glmToBullet(orientation); btVector3 bodyPosition = glmToBullet(position + orientation * _shapeLocalOffset); _avatarBodyTransform = btTransform(bodyOrientation, bodyPosition); }
void DynamicCharacterController::preSimulation(btScalar timeStep) { if (_enabled && _dynamicsWorld) { glm::quat rotation = _avatarData->getOrientation(); // TODO: update gravity if up has changed updateUpAxis(rotation); glm::vec3 position = _avatarData->getPosition() + rotation * _shapeLocalOffset; _rigidBody->setWorldTransform(btTransform(glmToBullet(rotation), glmToBullet(position))); // the rotation is dictated by AvatarData btTransform xform = _rigidBody->getWorldTransform(); xform.setRotation(glmToBullet(rotation)); _rigidBody->setWorldTransform(xform); // scan for distant floor // rayStart is at center of bottom sphere btVector3 rayStart = xform.getOrigin() - _halfHeight * _currentUp; // rayEnd is straight down MAX_FALL_HEIGHT btScalar rayLength = _radius + MAX_FALL_HEIGHT; btVector3 rayEnd = rayStart - rayLength * _currentUp; ClosestNotMe rayCallback(_rigidBody); rayCallback.m_closestHitFraction = 1.0f; _dynamicsWorld->rayTest(rayStart, rayEnd, rayCallback); if (rayCallback.hasHit()) { _floorDistance = rayLength * rayCallback.m_closestHitFraction - _radius; const btScalar MIN_HOVER_HEIGHT = 3.0f; if (_isHovering && _floorDistance < MIN_HOVER_HEIGHT && !_isPushingUp) { setHovering(false); } // TODO: use collision events rather than ray-trace test to disable jumping const btScalar JUMP_PROXIMITY_THRESHOLD = 0.1f * _radius; if (_floorDistance < JUMP_PROXIMITY_THRESHOLD) { _isJumping = false; } } else { _floorDistance = FLT_MAX; setHovering(true); } _walkVelocity = glmToBullet(_avatarData->getTargetVelocity()); if (_pendingFlags & PENDING_FLAG_JUMP) { _pendingFlags &= ~ PENDING_FLAG_JUMP; if (onGround()) { _isJumping = true; btVector3 velocity = _rigidBody->getLinearVelocity(); velocity += _jumpSpeed * _currentUp; _rigidBody->setLinearVelocity(velocity); } } } }