Merge pull request #8446 from sethalves/local-velocity-for-scripts

Local velocity for scripts
This commit is contained in:
Brad Hefta-Gaub 2016-08-17 09:06:54 -07:00 committed by GitHub
commit cd28df6c2e
7 changed files with 136 additions and 31 deletions

View file

@ -325,6 +325,8 @@ EntityPropertyFlags EntityItemProperties::getChangedProperties() const {
CHECK_PROPERTY_CHANGE(PROP_QUERY_AA_CUBE, queryAACube);
CHECK_PROPERTY_CHANGE(PROP_LOCAL_POSITION, localPosition);
CHECK_PROPERTY_CHANGE(PROP_LOCAL_ROTATION, localRotation);
CHECK_PROPERTY_CHANGE(PROP_LOCAL_VELOCITY, localVelocity);
CHECK_PROPERTY_CHANGE(PROP_LOCAL_ANGULAR_VELOCITY, localAngularVelocity);
CHECK_PROPERTY_CHANGE(PROP_FLYING_ALLOWED, flyingAllowed);
CHECK_PROPERTY_CHANGE(PROP_GHOSTING_ALLOWED, ghostingAllowed);
@ -570,6 +572,8 @@ QScriptValue EntityItemProperties::copyToScriptValue(QScriptEngine* engine, bool
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LOCAL_POSITION, localPosition);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LOCAL_ROTATION, localRotation);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LOCAL_VELOCITY, localVelocity);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LOCAL_ANGULAR_VELOCITY, localAngularVelocity);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_CLIENT_ONLY, clientOnly);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_OWNING_AVATAR_ID, owningAvatarID);
@ -707,6 +711,8 @@ void EntityItemProperties::copyFromScriptValue(const QScriptValue& object, bool
COPY_PROPERTY_FROM_QSCRIPTVALUE(localPosition, glmVec3, setLocalPosition);
COPY_PROPERTY_FROM_QSCRIPTVALUE(localRotation, glmQuat, setLocalRotation);
COPY_PROPERTY_FROM_QSCRIPTVALUE(localVelocity, glmVec3, setLocalVelocity);
COPY_PROPERTY_FROM_QSCRIPTVALUE(localAngularVelocity, glmVec3, setLocalAngularVelocity);
COPY_PROPERTY_FROM_QSCRIPTVALUE(jointRotationsSet, qVectorBool, setJointRotationsSet);
COPY_PROPERTY_FROM_QSCRIPTVALUE(jointRotations, qVectorQuat, setJointRotations);
@ -864,6 +870,8 @@ void EntityItemProperties::entityPropertyFlagsFromScriptValue(const QScriptValue
ADD_PROPERTY_TO_MAP(PROP_LOCAL_POSITION, LocalPosition, localPosition, glm::vec3);
ADD_PROPERTY_TO_MAP(PROP_LOCAL_ROTATION, LocalRotation, localRotation, glm::quat);
ADD_PROPERTY_TO_MAP(PROP_LOCAL_VELOCITY, LocalVelocity, localVelocity, glm::vec3);
ADD_PROPERTY_TO_MAP(PROP_LOCAL_ANGULAR_VELOCITY, LocalAngularVelocity, localAngularVelocity, glm::vec3);
ADD_PROPERTY_TO_MAP(PROP_JOINT_ROTATIONS_SET, JointRotationsSet, jointRotationsSet, QVector<bool>);
ADD_PROPERTY_TO_MAP(PROP_JOINT_ROTATIONS, JointRotations, jointRotations, QVector<glm::quat>);
@ -1982,7 +1990,9 @@ QList<QString> EntityItemProperties::listChangedProperties() {
}
bool EntityItemProperties::parentDependentPropertyChanged() const {
return localPositionChanged() || positionChanged() || localRotationChanged() || rotationChanged();
return localPositionChanged() || positionChanged() ||
localRotationChanged() || rotationChanged() ||
localVelocityChanged() || localAngularVelocityChanged();
}
bool EntityItemProperties::parentRelatedPropertyChanged() const {

View file

@ -201,6 +201,8 @@ public:
// these are used when bouncing location data into and out of scripts
DEFINE_PROPERTY_REF(PROP_LOCAL_POSITION, LocalPosition, localPosition, glmVec3, ENTITY_ITEM_ZERO_VEC3);
DEFINE_PROPERTY_REF(PROP_LOCAL_ROTATION, LocalRotation, localRotation, glmQuat, ENTITY_ITEM_DEFAULT_ROTATION);
DEFINE_PROPERTY_REF(PROP_LOCAL_VELOCITY, LocalVelocity, localVelocity, glmVec3, ENTITY_ITEM_ZERO_VEC3);
DEFINE_PROPERTY_REF(PROP_LOCAL_ANGULAR_VELOCITY, LocalAngularVelocity, localAngularVelocity, glmVec3, ENTITY_ITEM_ZERO_VEC3);
DEFINE_PROPERTY_REF(PROP_JOINT_ROTATIONS_SET, JointRotationsSet, jointRotationsSet, QVector<bool>, QVector<bool>());
DEFINE_PROPERTY_REF(PROP_JOINT_ROTATIONS, JointRotations, jointRotations, QVector<glm::quat>, QVector<glm::quat>());

View file

@ -177,6 +177,9 @@ enum EntityPropertyList {
PROP_SHAPE,
PROP_LOCAL_VELOCITY, // only used to convert values to and from scripts
PROP_LOCAL_ANGULAR_VELOCITY, // only used to convert values to and from scripts
////////////////////////////////////////////////////////////////////////////////////////////////////
// ATTENTION: add new properties to end of list just ABOVE this line
PROP_AFTER_LAST_ITEM,

View file

@ -78,6 +78,8 @@ EntityItemProperties convertLocationToScriptSemantics(const EntityItemProperties
EntityItemProperties scriptSideProperties = entitySideProperties;
scriptSideProperties.setLocalPosition(entitySideProperties.getPosition());
scriptSideProperties.setLocalRotation(entitySideProperties.getRotation());
scriptSideProperties.setLocalVelocity(entitySideProperties.getLocalVelocity());
scriptSideProperties.setLocalAngularVelocity(entitySideProperties.getLocalAngularVelocity());
bool success;
glm::vec3 worldPosition = SpatiallyNestable::localToWorld(entitySideProperties.getPosition(),
@ -88,10 +90,19 @@ EntityItemProperties convertLocationToScriptSemantics(const EntityItemProperties
entitySideProperties.getParentID(),
entitySideProperties.getParentJointIndex(),
success);
// TODO -- handle velocity and angularVelocity
glm::vec3 worldVelocity = SpatiallyNestable::localToWorldVelocity(entitySideProperties.getVelocity(),
entitySideProperties.getParentID(),
entitySideProperties.getParentJointIndex(),
success);
glm::vec3 worldAngularVelocity = SpatiallyNestable::localToWorldAngularVelocity(entitySideProperties.getAngularVelocity(),
entitySideProperties.getParentID(),
entitySideProperties.getParentJointIndex(),
success);
scriptSideProperties.setPosition(worldPosition);
scriptSideProperties.setRotation(worldRotation);
scriptSideProperties.setVelocity(worldVelocity);
scriptSideProperties.setAngularVelocity(worldAngularVelocity);
return scriptSideProperties;
}
@ -125,6 +136,27 @@ EntityItemProperties convertLocationFromScriptSemantics(const EntityItemProperti
entitySideProperties.setRotation(localRotation);
}
if (scriptSideProperties.localVelocityChanged()) {
entitySideProperties.setVelocity(scriptSideProperties.getLocalVelocity());
} else if (scriptSideProperties.velocityChanged()) {
glm::vec3 localVelocity = SpatiallyNestable::worldToLocalVelocity(entitySideProperties.getVelocity(),
entitySideProperties.getParentID(),
entitySideProperties.getParentJointIndex(),
success);
entitySideProperties.setVelocity(localVelocity);
}
if (scriptSideProperties.localAngularVelocityChanged()) {
entitySideProperties.setAngularVelocity(scriptSideProperties.getLocalAngularVelocity());
} else if (scriptSideProperties.angularVelocityChanged()) {
glm::vec3 localAngularVelocity =
SpatiallyNestable::worldToLocalAngularVelocity(entitySideProperties.getAngularVelocity(),
entitySideProperties.getParentID(),
entitySideProperties.getParentJointIndex(),
success);
entitySideProperties.setAngularVelocity(localAngularVelocity);
}
return entitySideProperties;
}

View file

@ -224,6 +224,38 @@ glm::quat SpatiallyNestable::worldToLocal(const glm::quat& orientation,
return result.getRotation();
}
glm::vec3 SpatiallyNestable::worldToLocalVelocity(const glm::vec3& velocity, const QUuid& parentID,
int parentJointIndex, bool& success) {
SpatiallyNestablePointer parent = SpatiallyNestable::findByID(parentID, success);
if (!success || !parent) {
return velocity;
}
Transform parentTransform = parent->getTransform(success);
if (!success) {
return velocity;
}
glm::vec3 parentVelocity = parent->getVelocity(success);
if (!success) {
return velocity;
}
return glm::inverse(parentTransform.getRotation()) * (velocity - parentVelocity);
}
glm::vec3 SpatiallyNestable::worldToLocalAngularVelocity(const glm::vec3& angularVelocity, const QUuid& parentID,
int parentJointIndex, bool& success) {
SpatiallyNestablePointer parent = SpatiallyNestable::findByID(parentID, success);
if (!success || !parent) {
return angularVelocity;
}
Transform parentTransform = parent->getTransform(success);
if (!success) {
return angularVelocity;
}
return glm::inverse(parentTransform.getRotation()) * angularVelocity;
}
glm::vec3 SpatiallyNestable::localToWorld(const glm::vec3& position,
const QUuid& parentID, int parentJointIndex,
bool& success) {
@ -298,6 +330,38 @@ glm::quat SpatiallyNestable::localToWorld(const glm::quat& orientation,
return result.getRotation();
}
glm::vec3 SpatiallyNestable::localToWorldVelocity(const glm::vec3& velocity, const QUuid& parentID,
int parentJointIndex, bool& success) {
SpatiallyNestablePointer parent = SpatiallyNestable::findByID(parentID, success);
if (!success || !parent) {
return velocity;
}
Transform parentTransform = parent->getTransform(success);
if (!success) {
return velocity;
}
glm::vec3 parentVelocity = parent->getVelocity(success);
if (!success) {
return velocity;
}
return parentVelocity + parentTransform.getRotation() * velocity;
}
glm::vec3 SpatiallyNestable::localToWorldAngularVelocity(const glm::vec3& angularVelocity, const QUuid& parentID,
int parentJointIndex, bool& success) {
SpatiallyNestablePointer parent = SpatiallyNestable::findByID(parentID, success);
if (!success || !parent) {
return angularVelocity;
}
Transform parentTransform = parent->getTransform(success);
if (!success) {
return angularVelocity;
}
return parentTransform.getRotation() * angularVelocity;
}
glm::vec3 SpatiallyNestable::getPosition(bool& success) const {
return getTransform(success).getTranslation();
}
@ -1004,3 +1068,15 @@ void SpatiallyNestable::setLocalTransformAndVelocities(
locationChanged(false);
}
}
SpatiallyNestablePointer SpatiallyNestable::findByID(QUuid id, bool& success) {
QSharedPointer<SpatialParentFinder> parentFinder = DependencyManager::get<SpatialParentFinder>();
if (!parentFinder) {
return nullptr;
}
SpatiallyNestableWeakPointer parentWP = parentFinder->find(id, success);
if (!success) {
return nullptr;
}
return parentWP.lock();
}

View file

@ -48,9 +48,17 @@ public:
static glm::vec3 worldToLocal(const glm::vec3& position, const QUuid& parentID, int parentJointIndex, bool& success);
static glm::quat worldToLocal(const glm::quat& orientation, const QUuid& parentID, int parentJointIndex, bool& success);
static glm::vec3 worldToLocalVelocity(const glm::vec3& velocity, const QUuid& parentID,
int parentJointIndex, bool& success);
static glm::vec3 worldToLocalAngularVelocity(const glm::vec3& angularVelocity, const QUuid& parentID,
int parentJointIndex, bool& success);
static glm::vec3 localToWorld(const glm::vec3& position, const QUuid& parentID, int parentJointIndex, bool& success);
static glm::quat localToWorld(const glm::quat& orientation, const QUuid& parentID, int parentJointIndex, bool& success);
static glm::vec3 localToWorldVelocity(const glm::vec3& velocity,
const QUuid& parentID, int parentJointIndex, bool& success);
static glm::vec3 localToWorldAngularVelocity(const glm::vec3& angularVelocity,
const QUuid& parentID, int parentJointIndex, bool& success);
// world frame
virtual const Transform getTransform(bool& success, int depth = 0) const;
@ -151,6 +159,8 @@ public:
virtual SpatialParentTree* getParentTree() const { return nullptr; }
bool hasAncestorOfType(NestableType nestableType);
SpatiallyNestablePointer getParentPointer(bool& success) const;
static SpatiallyNestablePointer findByID(QUuid id, bool& success);
void getLocalTransformAndVelocities(Transform& localTransform,
glm::vec3& localVelocity,
@ -166,7 +176,6 @@ protected:
QUuid _id;
QUuid _parentID; // what is this thing's transform relative to?
quint16 _parentJointIndex { 0 }; // which joint of the parent is this relative to?
SpatiallyNestablePointer getParentPointer(bool& success) const;
mutable SpatiallyNestableWeakPointer _parent;

View file

@ -2204,28 +2204,13 @@ function MyController(hand) {
var props = Entities.getEntityProperties(entityID, ["parentID", "velocity", "dynamic", "shapeType"]);
var parentID = props.parentID;
var doSetVelocity = false;
if (parentID != NULL_UUID && deactiveProps.parentID == NULL_UUID && propsArePhysical(props)) {
// TODO: EntityScriptingInterface::convertLocationToScriptSemantics should be setting up
// props.velocity to be a world-frame velocity and localVelocity to be vs parent. Until that
// is done, we use a measured velocity here so that things held via a bumper-grab / parenting-grab
// can be thrown.
doSetVelocity = true;
}
if (!noVelocity &&
!doSetVelocity &&
parentID == MyAvatar.sessionUUID &&
Vec3.length(data["gravity"]) > 0.0 &&
data["dynamic"] &&
data["parentID"] == NULL_UUID &&
!data["collisionless"]) {
deactiveProps["velocity"] = {
x: 0.0,
y: 0.1,
z: 0.0
};
doSetVelocity = false;
deactiveProps["velocity"] = this.currentVelocity;
}
if (noVelocity) {
deactiveProps["velocity"] = {
@ -2238,21 +2223,9 @@ function MyController(hand) {
y: 0.0,
z: 0.0
};
doSetVelocity = false;
}
Entities.editEntity(entityID, deactiveProps);
if (doSetVelocity) {
// this is a continuation of the TODO above -- we shouldn't need to set this here.
// do this after the parent has been reset. setting this at the same time as
// the parent causes it to go off in the wrong direction. This is a bug that should
// be fixed.
Entities.editEntity(entityID, {
velocity: this.currentVelocity
// angularVelocity: this.currentAngularVelocity
});
}
data = null;
} else if (this.shouldResetParentOnRelease) {
// we parent-grabbed this from another parent grab. try to put it back where we found it.