bid immediately when creating new entity

also clear EntityMotionState::_numInactiveUpdates on new ownership
This commit is contained in:
Andrew Meadows 2017-06-01 14:17:14 -07:00
parent 74827fc4c8
commit 29a05d7eb4
7 changed files with 38 additions and 48 deletions

View file

@ -1295,27 +1295,15 @@ void EntityItem::getAllTerseUpdateProperties(EntityItemProperties& properties) c
properties._accelerationChanged = true;
}
void EntityItem::pokeSimulationOwnership() {
markDirtyFlags(Simulation::DIRTY_SIMULATION_OWNERSHIP_FOR_POKE);
void EntityItem::flagForOwnershipBid(uint8_t priority) {
markDirtyFlags(Simulation::DIRTY_SIMULATION_OWNERSHIP_PRIORITY);
auto nodeList = DependencyManager::get<NodeList>();
if (_simulationOwner.matchesValidID(nodeList->getSessionUUID())) {
// we already own it
_simulationOwner.promotePriority(SCRIPT_POKE_SIMULATION_PRIORITY);
_simulationOwner.promotePriority(priority);
} else {
// we don't own it yet
_simulationOwner.setPendingPriority(SCRIPT_POKE_SIMULATION_PRIORITY, usecTimestampNow());
}
}
void EntityItem::grabSimulationOwnership() {
markDirtyFlags(Simulation::DIRTY_SIMULATION_OWNERSHIP_FOR_GRAB);
auto nodeList = DependencyManager::get<NodeList>();
if (_simulationOwner.matchesValidID(nodeList->getSessionUUID())) {
// we already own it
_simulationOwner.promotePriority(SCRIPT_GRAB_SIMULATION_PRIORITY);
} else {
// we don't own it yet
_simulationOwner.setPendingPriority(SCRIPT_GRAB_SIMULATION_PRIORITY, usecTimestampNow());
_simulationOwner.setPendingPriority(priority, usecTimestampNow());
}
}

View file

@ -321,6 +321,7 @@ public:
void updateSimulationOwner(const SimulationOwner& owner);
void clearSimulationOwnership();
void setPendingOwnershipPriority(quint8 priority, const quint64& timestamp);
uint8_t getPendingOwnershipPriority() const { return _simulationOwner.getPendingPriority(); }
void rememberHasSimulationOwnershipBid() const;
QString getMarketplaceID() const;
@ -394,8 +395,7 @@ public:
void getAllTerseUpdateProperties(EntityItemProperties& properties) const;
void pokeSimulationOwnership();
void grabSimulationOwnership();
void flagForOwnershipBid(uint8_t priority);
void flagForMotionStateChange() { _dirtyFlags |= Simulation::DIRTY_MOTION_TYPE; }
QString actionsToDebugString();

View file

@ -230,6 +230,8 @@ QUuid EntityScriptingInterface::addEntity(const EntityItemProperties& properties
}
entity->setLastBroadcast(usecTimestampNow());
// since we're creating this object we will immediately volunteer to own its simulation
entity->flagForOwnershipBid(VOLUNTEER_SIMULATION_PRIORITY);
propertiesWithSimID.setLastEdited(entity->getLastEdited());
} else {
qCDebug(entities) << "script failed to add new Entity to local Octree";
@ -440,7 +442,7 @@ QUuid EntityScriptingInterface::editEntity(QUuid id, const EntityItemProperties&
} else {
// we make a bid for simulation ownership
properties.setSimulationOwner(myNodeID, SCRIPT_POKE_SIMULATION_PRIORITY);
entity->pokeSimulationOwnership();
entity->flagForOwnershipBid(SCRIPT_POKE_SIMULATION_PRIORITY);
entity->rememberHasSimulationOwnershipBid();
}
}
@ -1194,7 +1196,7 @@ QUuid EntityScriptingInterface::addAction(const QString& actionTypeString,
}
action->setIsMine(true);
success = entity->addAction(simulation, action);
entity->grabSimulationOwnership();
entity->flagForOwnershipBid(SCRIPT_GRAB_SIMULATION_PRIORITY);
return false; // Physics will cause a packet to be sent, so don't send from here.
});
if (success) {
@ -1210,7 +1212,7 @@ bool EntityScriptingInterface::updateAction(const QUuid& entityID, const QUuid&
return actionWorker(entityID, [&](EntitySimulationPointer simulation, EntityItemPointer entity) {
bool success = entity->updateAction(simulation, actionID, arguments);
if (success) {
entity->grabSimulationOwnership();
entity->flagForOwnershipBid(SCRIPT_GRAB_SIMULATION_PRIORITY);
}
return success;
});
@ -1224,7 +1226,7 @@ bool EntityScriptingInterface::deleteAction(const QUuid& entityID, const QUuid&
success = entity->removeAction(simulation, actionID);
if (success) {
// reduce from grab to poke
entity->pokeSimulationOwnership();
entity->flagForOwnershipBid(SCRIPT_POKE_SIMULATION_PRIORITY);
}
return false; // Physics will cause a packet to be sent, so don't send from here.
});

View file

@ -26,12 +26,10 @@ namespace Simulation {
const uint32_t DIRTY_MATERIAL = 0x00400;
const uint32_t DIRTY_PHYSICS_ACTIVATION = 0x0800; // should activate object in physics engine
const uint32_t DIRTY_SIMULATOR_ID = 0x1000; // the simulatorID has changed
const uint32_t DIRTY_SIMULATION_OWNERSHIP_FOR_POKE = 0x2000; // bid for simulation ownership at "poke"
const uint32_t DIRTY_SIMULATION_OWNERSHIP_FOR_GRAB = 0x4000; // bid for simulation ownership at "grab"
const uint32_t DIRTY_SIMULATION_OWNERSHIP_PRIORITY = 0x2000; // our own bid priority has changed
const uint32_t DIRTY_TRANSFORM = DIRTY_POSITION | DIRTY_ROTATION;
const uint32_t DIRTY_VELOCITIES = DIRTY_LINEAR_VELOCITY | DIRTY_ANGULAR_VELOCITY;
const uint32_t DIRTY_SIMULATION_OWNERSHIP_PRIORITY = DIRTY_SIMULATION_OWNERSHIP_FOR_POKE | DIRTY_SIMULATION_OWNERSHIP_FOR_GRAB;
};
#endif // hifi_SimulationFlags_h

View file

@ -26,9 +26,9 @@ const int SimulationOwner::NUM_BYTES_ENCODED = NUM_BYTES_RFC4122_UUID + 1;
SimulationOwner::SimulationOwner() :
_id(),
_expiry(0),
_pendingTimestamp(0),
_pendingBidTimestamp(0),
_priority(0),
_pendingPriority(0),
_pendingBidPriority(0),
_pendingState(PENDING_STATE_NOTHING)
{
}
@ -36,9 +36,9 @@ SimulationOwner::SimulationOwner() :
SimulationOwner::SimulationOwner(const QUuid& id, quint8 priority) :
_id(id),
_expiry(0),
_pendingTimestamp(0),
_pendingBidTimestamp(0),
_priority(priority),
_pendingPriority(0)
_pendingBidPriority(0)
{
}
@ -61,9 +61,9 @@ bool SimulationOwner::fromByteArray(const QByteArray& data) {
void SimulationOwner::clear() {
_id = QUuid();
_expiry = 0;
_pendingTimestamp = 0;
_pendingBidTimestamp = 0;
_priority = 0;
_pendingPriority = 0;
_pendingBidPriority = 0;
_pendingState = PENDING_STATE_NOTHING;
}
@ -102,9 +102,9 @@ bool SimulationOwner::set(const SimulationOwner& owner) {
}
void SimulationOwner::setPendingPriority(quint8 priority, const quint64& timestamp) {
_pendingPriority = priority;
_pendingTimestamp = timestamp;
_pendingState = (_pendingPriority == 0) ? PENDING_STATE_RELEASE : PENDING_STATE_TAKE;
_pendingBidPriority = priority;
_pendingBidTimestamp = timestamp;
_pendingState = (_pendingBidPriority == 0) ? PENDING_STATE_RELEASE : PENDING_STATE_TAKE;
}
void SimulationOwner::updateExpiry() {
@ -113,11 +113,11 @@ void SimulationOwner::updateExpiry() {
}
bool SimulationOwner::pendingRelease(const quint64& timestamp) {
return _pendingPriority == 0 && _pendingState == PENDING_STATE_RELEASE && _pendingTimestamp >= timestamp;
return _pendingBidPriority == 0 && _pendingState == PENDING_STATE_RELEASE && _pendingBidTimestamp >= timestamp;
}
bool SimulationOwner::pendingTake(const quint64& timestamp) {
return _pendingPriority > 0 && _pendingState == PENDING_STATE_TAKE && _pendingTimestamp >= timestamp;
return _pendingBidPriority > 0 && _pendingState == PENDING_STATE_TAKE && _pendingBidTimestamp >= timestamp;
}
void SimulationOwner::clearCurrentOwner() {

View file

@ -66,6 +66,7 @@ public:
bool hasExpired() const { return usecTimestampNow() > _expiry; }
uint8_t getPendingPriority() const { return _pendingBidPriority; }
bool pendingRelease(const quint64& timestamp); // return true if valid pending RELEASE
bool pendingTake(const quint64& timestamp); // return true if valid pending TAKE
void clearCurrentOwner();
@ -84,9 +85,9 @@ public:
private:
QUuid _id; // owner
quint64 _expiry; // time when ownership can transition at equal priority
quint64 _pendingTimestamp; // time when pending update was set
quint64 _pendingBidTimestamp; // time when pending bid was set
quint8 _priority; // priority of current owner
quint8 _pendingPriority; // priority of pendingTake
quint8 _pendingBidPriority; // priority at which we'd like to own it
quint8 _pendingState; // NOTHING, TAKE, or RELEASE
};

View file

@ -65,8 +65,7 @@ EntityMotionState::EntityMotionState(btCollisionShape* shape, EntityItemPointer
_lastStep(0),
_loopsWithoutOwner(0),
_accelerationNearlyGravityCount(0),
_numInactiveUpdates(1),
_outgoingPriority(0)
_numInactiveUpdates(1)
{
_type = MOTIONSTATE_TYPE_ENTITY;
assert(_entity);
@ -75,6 +74,8 @@ EntityMotionState::EntityMotionState(btCollisionShape* shape, EntityItemPointer
// we need the side-effects of EntityMotionState::setShape() so we call it explicitly here
// rather than pass the legit shape pointer to the ObjectMotionState ctor above.
setShape(shape);
_outgoingPriority = _entity->getPendingOwnershipPriority();
}
EntityMotionState::~EntityMotionState() {
@ -135,23 +136,23 @@ void EntityMotionState::handleEasyChanges(uint32_t& flags) {
_nextOwnershipBid = usecTimestampNow() + USECS_BETWEEN_OWNERSHIP_BIDS;
}
_loopsWithoutOwner = 0;
_numInactiveUpdates = 0;
} else if (isLocallyOwned()) {
// we just inherited ownership, make sure our desired priority matches what we have
upgradeOutgoingPriority(_entity->getSimulationPriority());
} else {
_outgoingPriority = 0;
_nextOwnershipBid = usecTimestampNow() + USECS_BETWEEN_OWNERSHIP_BIDS;
_numInactiveUpdates = 0;
}
}
if (flags & Simulation::DIRTY_SIMULATION_OWNERSHIP_PRIORITY) {
// The DIRTY_SIMULATOR_OWNERSHIP_PRIORITY bits really mean "we should bid for ownership because
// a local script has been changing physics properties, or we should adjust our own ownership priority".
// The desired priority is determined by which bits were set.
if (flags & Simulation::DIRTY_SIMULATION_OWNERSHIP_FOR_GRAB) {
_outgoingPriority = SCRIPT_GRAB_SIMULATION_PRIORITY;
} else {
_outgoingPriority = SCRIPT_POKE_SIMULATION_PRIORITY;
}
// The DIRTY_SIMULATOR_OWNERSHIP_PRIORITY bit means one of the following:
// (1) we own it but may need to change the priority OR...
// (2) we don't own it but should bid (because a local script has been changing physics properties)
uint8_t newPriority = isLocallyOwned() ? _entity->getSimulationOwner().getPriority() : _entity->getSimulationOwner().getPendingPriority();
_outgoingPriority = glm::max(_outgoingPriority, newPriority);
// reset bid expiry so that we bid ASAP
_nextOwnershipBid = 0;
}