Merge branch 'master' of https://github.com/highfidelity/hifi into zone-visibility

This commit is contained in:
Howard Stearns 2016-03-14 22:05:41 -07:00
commit 28f5ee16b8
34 changed files with 171 additions and 89 deletions

View file

@ -213,7 +213,6 @@ function AttachedEntitiesManager() {
var props = Entities.getEntityProperties(entityID);
if (props.parentID == MyAvatar.sessionUUID) {
grabData = getEntityCustomData('grabKey', entityID, {});
grabbableData = getEntityCustomData('grabbableKey', entityID, {});
var wearableData = getEntityCustomData('wearable', entityID, DEFAULT_WEARABLE_DATA);
var currentJointName = MyAvatar.getJointNames()[props.parentJointIndex];
wearableData.joints[currentJointName] = [props.localPosition, props.localRotation];

View file

@ -1006,7 +1006,7 @@ function MyController(hand) {
// else this thing isn't physical. grab it by reparenting it (but not if we've already
// grabbed it).
if (grabbableData.refCount < 1) {
if (refCount < 1) {
this.setState(this.state == STATE_SEARCHING ? STATE_NEAR_GRABBING : STATE_EQUIP);
return;
} else {
@ -1120,7 +1120,6 @@ function MyController(hand) {
var controllerRotation = Quat.multiply(MyAvatar.orientation, avatarControllerPose.rotation);
var grabbedProperties = Entities.getEntityProperties(this.grabbedEntity, GRABBABLE_PROPERTIES);
var grabbableData = getEntityCustomData(GRABBABLE_DATA_KEY, this.grabbedEntity, DEFAULT_GRABBABLE_DATA);
if (this.state == STATE_CONTINUE_DISTANCE_HOLDING && this.bumperSqueezed() &&
this.hasPresetOffsets()) {
@ -1307,7 +1306,6 @@ function MyController(hand) {
this.nearGrabbing = function() {
var now = Date.now();
var grabbableData = getEntityCustomData(GRABBABLE_DATA_KEY, this.grabbedEntity, DEFAULT_GRABBABLE_DATA);
if (this.state == STATE_NEAR_GRABBING && this.triggerSmoothedReleased()) {
this.setState(STATE_RELEASE);
@ -1330,10 +1328,9 @@ function MyController(hand) {
var handRotation = (this.hand === RIGHT_HAND) ? MyAvatar.getRightPalmRotation() : MyAvatar.getLeftPalmRotation();
var handPosition = this.getHandPosition();
var grabbableData = getEntityCustomData(GRABBABLE_DATA_KEY, this.grabbedEntity, DEFAULT_GRABBABLE_DATA);
var hasPresetPosition = false;
if (this.state != STATE_NEAR_GRABBING && this.hasPresetOffsets()) {
var grabbableData = getEntityCustomData(GRABBABLE_DATA_KEY, this.grabbedEntity, DEFAULT_GRABBABLE_DATA);
// if an object is "equipped" and has a predefined offset, use it.
this.ignoreIK = grabbableData.ignoreIK ? grabbableData.ignoreIK : false;
this.offsetPosition = this.getPresetPosition();
@ -1676,7 +1673,6 @@ function MyController(hand) {
};
this.activateEntity = function(entityID, grabbedProperties, wasLoaded) {
var grabbableData = getEntityCustomData(GRABBABLE_DATA_KEY, entityID, DEFAULT_GRABBABLE_DATA);
var data = getEntityCustomData(GRAB_USER_DATA_KEY, entityID, {});
var now = Date.now();

View file

@ -243,6 +243,41 @@
}
function userDataChanger(groupName, keyName, checkBoxElement, userDataElement, defaultValue) {
var properties = {};
var parsedData = {};
try {
parsedData = JSON.parse(userDataElement.value);
} catch(e) {}
if (!(groupName in parsedData)) {
parsedData[groupName] = {}
}
delete parsedData[groupName][keyName];
if (checkBoxElement.checked !== defaultValue) {
parsedData[groupName][keyName] = checkBoxElement.checked;
}
if (Object.keys(parsedData[groupName]).length == 0) {
delete parsedData[groupName];
}
if (Object.keys(parsedData).length > 0) {
properties['userData'] = JSON.stringify(parsedData);
} else {
properties['userData'] = '';
}
userDataElement.value = properties['userData'];
EventBridge.emitWebEvent(
JSON.stringify({
type: "update",
properties: properties,
})
);
};
function loaded() {
openEventBridge(function() {
var allSections = [];
@ -305,6 +340,11 @@
var elCollideMyAvatar = document.getElementById("property-collide-myAvatar");
var elCollideOtherAvatar = document.getElementById("property-collide-otherAvatar");
var elCollisionSoundURL = document.getElementById("property-collision-sound-url");
var elGrabbable = document.getElementById("property-grabbable");
var elWantsTrigger = document.getElementById("property-wants-trigger");
var elIgnoreIK = document.getElementById("property-ignore-ik");
var elLifetime = document.getElementById("property-lifetime");
var elScriptURL = document.getElementById("property-script-url");
var elScriptTimestamp = document.getElementById("property-script-timestamp");
@ -408,7 +448,7 @@
var elXTextureURL = document.getElementById("property-x-texture-url");
var elYTextureURL = document.getElementById("property-y-texture-url");
var elZTextureURL = document.getElementById("property-z-texture-url");
var elPreviewCameraButton = document.getElementById("preview-camera-button");
if (window.EventBridge !== undefined) {
@ -518,13 +558,30 @@
elCollisionless.checked = properties.collisionless;
elDynamic.checked = properties.dynamic;
elCollideStatic.checked = properties.collidesWith.indexOf("static") > -1;
elCollideKinematic.checked = properties.collidesWith.indexOf("kinematic") > -1;
elCollideDynamic.checked = properties.collidesWith.indexOf("dynamic") > -1;
elCollideMyAvatar.checked = properties.collidesWith.indexOf("myAvatar") > -1;
elCollideOtherAvatar.checked = properties.collidesWith.indexOf("otherAvatar") > -1;
elGrabbable.checked = properties.dynamic;
elWantsTrigger.checked = false;
elIgnoreIK.checked = false;
var parsedUserData = {}
try {
parsedUserData = JSON.parse(properties.userData);
} catch(e) {}
if ("grabbableKey" in parsedUserData) {
if ("grabbable" in parsedUserData["grabbableKey"]) {
elGrabbable.checked = parsedUserData["grabbableKey"].grabbable;
}
if ("wantsTrigger" in parsedUserData["grabbableKey"]) {
elWantsTrigger.checked = parsedUserData["grabbableKey"].wantsTrigger;
}
if ("ignoreIK" in parsedUserData["grabbableKey"]) {
elIgnoreIK.checked = parsedUserData["grabbableKey"].ignoreIK;
}
}
elCollisionSoundURL.value = properties.collisionSoundURL;
elLifetime.value = properties.lifetime;
@ -737,9 +794,6 @@
elCollisionless.addEventListener('change', createEmitCheckedPropertyUpdateFunction('collisionless'));
elDynamic.addEventListener('change', createEmitCheckedPropertyUpdateFunction('dynamic'));
elCollideDynamic.addEventListener('change', function() {
updateCheckedSubProperty("collidesWith", properties.collidesWith, elCollideDynamic, 'dynamic');
});
@ -758,6 +812,15 @@
updateCheckedSubProperty("collidesWith", properties.collidesWith, elCollideOtherAvatar, 'otherAvatar');
});
elGrabbable.addEventListener('change', function() {
userDataChanger("grabbableKey", "grabbable", elGrabbable, elUserData, properties.dynamic);
});
elWantsTrigger.addEventListener('change', function() {
userDataChanger("grabbableKey", "wantsTrigger", elWantsTrigger, elUserData, false);
});
elIgnoreIK.addEventListener('change', function() {
userDataChanger("grabbableKey", "ignoreIK", elIgnoreIK, elUserData, false);
});
elCollisionSoundURL.addEventListener('change', createEmitTextPropertyUpdateFunction('collisionSoundURL'));
@ -954,7 +1017,7 @@
action: "previewCamera"
}));
});
window.onblur = function() {
// Fake a change event
var ev = document.createEvent("HTMLEvents");
@ -1476,6 +1539,29 @@
</div>
</div>
<div class = "sub-section-header"> Grabbable: </div>
<div class = "sub-props-checkbox-group">
<div class="property">
<span class="label">grabbable</span>
<span class="value">
<input type='checkbox' id="property-grabbable">
</span>
</div>
<div class="property">
<span class="label">triggerable</span>
<span class="value">
<input type='checkbox' id="property-wants-trigger">
</span>
</div>
<div class="property">
<span class="label">ignore inverse-kinematics</span>
<span class="value">
<input type='checkbox' id="property-ignore-ik">
</span>
</div>
</div>
</div>

View file

@ -36,11 +36,11 @@ var AUDIO_LISTENER_MODE_CUSTOM = "Audio from custom position";
// be sure that the audio listener options are in the right order (same as the enumerator)
var AUDIO_LISTENER_OPTIONS = [
// MyAvatar.FROM_HEAD (0)
// MyAvatar.audioListenerModeHead (0)
AUDIO_LISTENER_MODE_FROM_HEAD,
// MyAvatar.FROM_CAMERA (1)
// MyAvatar.audioListenerModeCamera (1)
AUDIO_LISTENER_MODE_FROM_CAMERA,
// MyAvatar.CUSTOM (2)
// MyAvatar.audioListenerCustom (2)
AUDIO_LISTENER_MODE_CUSTOM
];
var AUDIO_STEREO_INPUT = "Stereo Input";

View file

@ -972,7 +972,6 @@ void Avatar::renderJointConnectingCone(gpu::Batch& batch, glm::vec3 position1, g
glm::vec3 perpCos = glm::normalize(glm::cross(axis, perpSin));
perpSin = glm::cross(perpCos, axis);
float anglea = 0.0f;
float angleb = 0.0f;
QVector<glm::vec3> points;
@ -980,7 +979,7 @@ void Avatar::renderJointConnectingCone(gpu::Batch& batch, glm::vec3 position1, g
// the rectangles that comprise the sides of the cone section are
// referenced by "a" and "b" in one dimension, and "1", and "2" in the other dimension.
anglea = angleb;
int anglea = angleb;
angleb = ((float)(i+1) / (float)NUM_BODY_CONE_SIDES) * TWO_PI;
float sa = sinf(anglea);

View file

@ -57,7 +57,7 @@ class Avatar : public AvatarData {
Q_PROPERTY(glm::vec3 skeletonOffset READ getSkeletonOffset WRITE setSkeletonOffset)
public:
Avatar(RigPointer rig = nullptr);
explicit Avatar(RigPointer rig = nullptr);
~Avatar();
typedef render::Payload<AvatarData> Payload;

View file

@ -308,7 +308,6 @@ bool AvatarActionHold::updateArguments(QVariantMap arguments) {
hand = _hand;
}
ok = true;
auto myAvatar = DependencyManager::get<AvatarManager>()->getMyAvatar();
holderID = myAvatar->getSessionUUID();

View file

@ -63,11 +63,11 @@ void AvatarManager::registerMetaTypes(QScriptEngine* engine) {
}
AvatarManager::AvatarManager(QObject* parent) :
_avatarFades()
_avatarFades(),
_myAvatar(std::make_shared<MyAvatar>(std::make_shared<Rig>()))
{
// register a meta type for the weak pointer we'll use for the owning avatar mixer for each avatar
qRegisterMetaType<QWeakPointer<Node> >("NodeWeakPointer");
_myAvatar = std::make_shared<MyAvatar>(std::make_shared<Rig>());
auto& packetReceiver = DependencyManager::get<NodeList>()->getPacketReceiver();
packetReceiver.registerListener(PacketType::BulkAvatarData, this, "processAvatarDataPacket");

View file

@ -71,8 +71,8 @@ public slots:
void updateAvatarRenderStatus(bool shouldRenderAvatars);
private:
AvatarManager(QObject* parent = 0);
AvatarManager(const AvatarManager& other);
explicit AvatarManager(QObject* parent = 0);
explicit AvatarManager(const AvatarManager& other);
void simulateAvatarFades(float deltaTime);

View file

@ -16,7 +16,7 @@
#include <display-plugins/DisplayPlugin.h>
#include "InterfaceLogging.h"
AvatarUpdate::AvatarUpdate() : GenericThread(), _lastAvatarUpdate(0) {
AvatarUpdate::AvatarUpdate() : GenericThread(), _lastAvatarUpdate(0), _isHMDMode(false) {
setObjectName("Avatar Update"); // GenericThread::initialize uses this to set the thread name.
Settings settings;
const int DEFAULT_TARGET_AVATAR_SIMRATE = 60;

View file

@ -28,7 +28,7 @@ class Avatar;
class Head : public HeadData {
public:
Head(Avatar* owningAvatar);
explicit Head(Avatar* owningAvatar);
void init();
void reset();

View file

@ -1522,9 +1522,9 @@ glm::vec3 MyAvatar::applyKeyboardMotor(float deltaTime, const glm::vec3& localVe
// (1) braking --> short timescale (aggressive motor assertion)
// (2) pushing --> medium timescale (mild motor assertion)
// (3) inactive --> long timescale (gentle friction for low speeds)
float MIN_KEYBOARD_MOTOR_TIMESCALE = 0.125f;
float MAX_KEYBOARD_MOTOR_TIMESCALE = 0.4f;
float MIN_KEYBOARD_BRAKE_SPEED = 0.3f;
const float MIN_KEYBOARD_MOTOR_TIMESCALE = 0.125f;
const float MAX_KEYBOARD_MOTOR_TIMESCALE = 0.4f;
const float MIN_KEYBOARD_BRAKE_SPEED = 0.3f;
float timescale = MAX_KEYBOARD_MOTOR_TIMESCALE;
bool isThrust = (glm::length2(_thrust) > EPSILON);
if (_isPushing || isThrust ||
@ -1787,7 +1787,7 @@ void MyAvatar::goToLocation(const glm::vec3& newPosition,
<< newOrientation.x << ", " << newOrientation.y << ", " << newOrientation.z << ", " << newOrientation.w;
// orient the user to face the target
glm::quat quatOrientation = newOrientation;
glm::quat quatOrientation = cancelOutRollAndPitch(newOrientation);
if (shouldFaceLocation) {
quatOrientation = newOrientation * glm::angleAxis(PI, glm::vec3(0.0f, 1.0f, 0.0f));

View file

@ -63,9 +63,9 @@ class MyAvatar : public Avatar {
Q_PROPERTY(AudioListenerMode audioListenerMode READ getAudioListenerMode WRITE setAudioListenerMode)
Q_PROPERTY(glm::vec3 customListenPosition READ getCustomListenPosition WRITE setCustomListenPosition)
Q_PROPERTY(glm::quat customListenOrientation READ getCustomListenOrientation WRITE setCustomListenOrientation)
Q_PROPERTY(AudioListenerMode FROM_HEAD READ getAudioListenerModeHead)
Q_PROPERTY(AudioListenerMode FROM_CAMERA READ getAudioListenerModeCamera)
Q_PROPERTY(AudioListenerMode CUSTOM READ getAudioListenerModeCustom)
Q_PROPERTY(AudioListenerMode audioListenerModeHead READ getAudioListenerModeHead)
Q_PROPERTY(AudioListenerMode audioListenerModeCamera READ getAudioListenerModeCamera)
Q_PROPERTY(AudioListenerMode audioListenerModeCustom READ getAudioListenerModeCustom)
//TODO: make gravity feature work Q_PROPERTY(glm::vec3 gravity READ getGravity WRITE setGravity)
@ -84,7 +84,7 @@ class MyAvatar : public Avatar {
Q_PROPERTY(float energy READ getEnergy WRITE setEnergy)
public:
MyAvatar(RigPointer rig);
explicit MyAvatar(RigPointer rig);
~MyAvatar();
virtual void simulateAttachments(float deltaTime) override;

View file

@ -46,14 +46,15 @@ void MyCharacterController::updateShapeIfNecessary() {
// NOTE: _shapeLocalOffset is already computed
if (_radius > 0.0f) {
// HACK: use some simple mass property defaults for now
float mass = 100.0f;
btVector3 inertia(30.0f, 8.0f, 30.0f);
// create RigidBody if it doesn't exist
if (!_rigidBody) {
// HACK: use some simple mass property defaults for now
const float DEFAULT_AVATAR_MASS = 100.0f;
const btVector3 DEFAULT_AVATAR_INERTIA_TENSOR(30.0f, 8.0f, 30.0f);
btCollisionShape* shape = new btCapsuleShape(_radius, 2.0f * _halfHeight);
_rigidBody = new btRigidBody(mass, nullptr, shape, inertia);
_rigidBody = new btRigidBody(DEFAULT_AVATAR_MASS, nullptr, shape, DEFAULT_AVATAR_INERTIA_TENSOR);
} else {
btCollisionShape* shape = _rigidBody->getCollisionShape();
if (shape) {

View file

@ -21,7 +21,7 @@ class MyAvatar;
class MyCharacterController : public CharacterController {
public:
MyCharacterController(MyAvatar* avatar);
explicit MyCharacterController(MyAvatar* avatar);
~MyCharacterController ();
virtual void updateShapeIfNecessary() override;

View file

@ -21,7 +21,7 @@
class AnimExpression {
public:
friend class AnimTests;
AnimExpression(const QString& str);
explicit AnimExpression(const QString& str);
protected:
struct Token {
enum Type {
@ -49,8 +49,8 @@ protected:
Comma,
Error
};
Token(Type type) : type {type} {}
Token(const QStringRef& strRef) : type {Type::Identifier}, strVal {strRef.toString()} {}
explicit Token(Type type) : type {type} {}
explicit Token(const QStringRef& strRef) : type {Type::Identifier}, strVal {strRef.toString()} {}
explicit Token(int val) : type {Type::Int}, intVal {val} {}
explicit Token(bool val) : type {Type::Bool}, intVal {val} {}
explicit Token(float val) : type {Type::Float}, floatVal {val} {}
@ -82,7 +82,7 @@ protected:
Modulus,
UnaryMinus
};
OpCode(Type type) : type {type} {}
explicit OpCode(Type type) : type {type} {}
explicit OpCode(const QStringRef& strRef) : type {Type::Identifier}, strVal {strRef.toString()} {}
explicit OpCode(const QString& str) : type {Type::Identifier}, strVal {str} {}
explicit OpCode(int val) : type {Type::Int}, intVal {val} {}

View file

@ -25,7 +25,7 @@ class RotationConstraint;
class AnimInverseKinematics : public AnimNode {
public:
AnimInverseKinematics(const QString& id);
explicit AnimInverseKinematics(const QString& id);
virtual ~AnimInverseKinematics() override;
void loadDefaultPoses(const AnimPoseVec& poses);

View file

@ -25,7 +25,7 @@ class AnimNodeLoader : public QObject {
Q_OBJECT
public:
AnimNodeLoader(const QUrl& url);
explicit AnimNodeLoader(const QUrl& url);
signals:
void success(AnimNode::Pointer node);

View file

@ -23,8 +23,8 @@ public:
using Pointer = std::shared_ptr<AnimSkeleton>;
using ConstPointer = std::shared_ptr<const AnimSkeleton>;
AnimSkeleton(const FBXGeometry& fbxGeometry);
AnimSkeleton(const std::vector<FBXJoint>& joints);
explicit AnimSkeleton(const FBXGeometry& fbxGeometry);
explicit AnimSkeleton(const std::vector<FBXJoint>& joints);
int nameToJointIndex(const QString& jointName) const;
const QString& getJointName(int jointIndex) const;
int getNumJoints() const;

View file

@ -110,7 +110,7 @@ protected:
public:
AnimStateMachine(const QString& id);
explicit AnimStateMachine(const QString& id);
virtual ~AnimStateMachine() override;
virtual const AnimPoseVec& evaluate(const AnimVariantMap& animVars, float dt, Triggers& triggersOut) override;

View file

@ -37,12 +37,12 @@ public:
static const AnimVariant False;
AnimVariant() : _type(Type::Bool) { memset(&_val, 0, sizeof(_val)); }
AnimVariant(bool value) : _type(Type::Bool) { _val.boolVal = value; }
AnimVariant(int value) : _type(Type::Int) { _val.intVal = value; }
AnimVariant(float value) : _type(Type::Float) { _val.floats[0] = value; }
AnimVariant(const glm::vec3& value) : _type(Type::Vec3) { *reinterpret_cast<glm::vec3*>(&_val) = value; }
AnimVariant(const glm::quat& value) : _type(Type::Quat) { *reinterpret_cast<glm::quat*>(&_val) = value; }
AnimVariant(const QString& value) : _type(Type::String) { _stringVal = value; }
explicit AnimVariant(bool value) : _type(Type::Bool) { _val.boolVal = value; }
explicit AnimVariant(int value) : _type(Type::Int) { _val.intVal = value; }
explicit AnimVariant(float value) : _type(Type::Float) { _val.floats[0] = value; }
explicit AnimVariant(const glm::vec3& value) : _type(Type::Vec3) { *reinterpret_cast<glm::vec3*>(&_val) = value; }
explicit AnimVariant(const glm::quat& value) : _type(Type::Quat) { *reinterpret_cast<glm::quat*>(&_val) = value; }
explicit AnimVariant(const QString& value) : _type(Type::String) { _stringVal = value; }
bool isBool() const { return _type == Type::Bool; }
bool isInt() const { return _type == Type::Int; }
@ -250,7 +250,7 @@ public:
qCDebug(animation) << " " << pair.first << "=" << pair.second.getString();
break;
default:
assert("AnimVariant::Type" == "valid");
assert(("invalid AnimVariant::Type", false));
}
}
}

View file

@ -38,7 +38,7 @@ protected:
virtual QSharedPointer<Resource> createResource(const QUrl& url,
const QSharedPointer<Resource>& fallback, bool delayLoad, const void* extra);
private:
AnimationCache(QObject* parent = NULL);
explicit AnimationCache(QObject* parent = NULL);
virtual ~AnimationCache() { }
};
@ -51,7 +51,7 @@ class Animation : public Resource {
public:
Animation(const QUrl& url);
explicit Animation(const QUrl& url);
const FBXGeometry& getGeometry() const { return *_geometry; }

View file

@ -40,6 +40,7 @@ AnimationLoop::AnimationLoop(const AnimationDetails& animationDetails) :
_lastFrame(animationDetails.lastFrame),
_running(animationDetails.running),
_currentFrame(animationDetails.currentFrame),
_maxFrameIndexHint(MAXIMUM_POSSIBLE_FRAME),
_resetOnRunning(true),
_lastSimulated(usecTimestampNow())
{
@ -55,6 +56,7 @@ AnimationLoop::AnimationLoop(float fps, bool loop, bool hold, bool startAutomati
_lastFrame(lastFrame),
_running(running),
_currentFrame(currentFrame),
_maxFrameIndexHint(MAXIMUM_POSSIBLE_FRAME),
_resetOnRunning(true),
_lastSimulated(usecTimestampNow())
{

View file

@ -19,7 +19,7 @@ public:
static const float MAXIMUM_POSSIBLE_FRAME;
AnimationLoop();
AnimationLoop(const AnimationDetails& animationDetails);
explicit AnimationLoop(const AnimationDetails& animationDetails);
AnimationLoop(float fps, bool loop, bool hold, bool startAutomatically, float firstFrame,
float lastFrame, bool running, float currentFrame);

View file

@ -37,17 +37,7 @@ static bool isEqual(const glm::quat& p, const glm::quat& q) {
return 1.0f - fabsf(glm::dot(p, q)) <= EPSILON;
}
#ifdef NDEBUG
#define ASSERT(cond)
#else
#define ASSERT(cond) \
do { \
if (!(cond)) { \
int* ptr = nullptr; \
*ptr = 10; \
} \
} while (0)
#endif
#define ASSERT(cond) assert(cond)
// 2 meter tall dude
const glm::vec3 DEFAULT_RIGHT_EYE_POS(-0.3f, 0.9f, 0.0f);

View file

@ -83,6 +83,7 @@ public:
Hover
};
Rig() {}
virtual ~Rig() {}
void destroyAnimGraph();

View file

@ -1115,7 +1115,7 @@ void AvatarData::detachOne(const QString& modelURL, const QString& jointName) {
return;
}
QVector<AttachmentData> attachmentData = getAttachmentData();
for (QVector<AttachmentData>::iterator it = attachmentData.begin(); it != attachmentData.end(); it++) {
for (QVector<AttachmentData>::iterator it = attachmentData.begin(); it != attachmentData.end(); ++it) {
if (it->modelURL == modelURL && (jointName.isEmpty() || it->jointName == jointName)) {
attachmentData.erase(it);
setAttachmentData(attachmentData);
@ -1134,7 +1134,7 @@ void AvatarData::detachAll(const QString& modelURL, const QString& jointName) {
if (it->modelURL == modelURL && (jointName.isEmpty() || it->jointName == jointName)) {
it = attachmentData.erase(it);
} else {
it++;
++it;
}
}
setAttachmentData(attachmentData);

View file

@ -42,6 +42,8 @@ HeadData::HeadData(AvatarData* owningAvatar) :
_rightEyeBlink(0.0f),
_averageLoudness(0.0f),
_browAudioLift(0.0f),
_audioAverageLoudness(0.0f),
_pupilDilation(0.0f),
_owningAvatar(owningAvatar)
{

View file

@ -32,7 +32,7 @@ class QJsonObject;
class HeadData {
public:
HeadData(AvatarData* owningAvatar);
explicit HeadData(AvatarData* owningAvatar);
virtual ~HeadData() { };
// degrees

View file

@ -34,7 +34,6 @@ void CongestionControl::setPacketSendPeriod(double newSendPeriod) {
}
DefaultCC::DefaultCC() :
_slowStartLastAck(_sendCurrSeqNum),
_lastDecreaseMaxSeq(SequenceNumber {SequenceNumber::MAX })
{
_mss = udt::MAX_PACKET_SIZE_WITH_UDP_HEADER;
@ -63,11 +62,11 @@ void DefaultCC::onACK(SequenceNumber ackNum) {
if (_slowStart) {
// we are in slow start phase - increase the congestion window size by the number of packets just ACKed
_congestionWindowSize += seqlen(_slowStartLastAck, ackNum);
_congestionWindowSize += seqlen(_slowStartLastACK, ackNum);
// update the last ACK
_slowStartLastAck = ackNum;
_slowStartLastACK = ackNum;
// check if we can get out of slow start (is our new congestion window size bigger than the max)
if (_congestionWindowSize > _maxCongestionWindowSize) {
_slowStart = false;

View file

@ -50,6 +50,7 @@ protected:
void setMaxCongestionWindowSize(int window) { _maxCongestionWindowSize = window; }
void setBandwidth(int bandwidth) { _bandwidth = bandwidth; }
void setMaxBandwidth(int maxBandwidth) { _maxBandwidth = maxBandwidth; }
virtual void setInitialSendSequenceNumber(SequenceNumber seqNum) = 0;
void setSendCurrentSequenceNumber(SequenceNumber seqNum) { _sendCurrSeqNum = seqNum; }
void setReceiveRate(int rate) { _receiveRate = rate; }
void setRTT(int rtt) { _rtt = rtt; }
@ -104,14 +105,17 @@ public:
virtual void onACK(SequenceNumber ackNum);
virtual void onLoss(SequenceNumber rangeStart, SequenceNumber rangeEnd);
virtual void onTimeout();
protected:
virtual void setInitialSendSequenceNumber(SequenceNumber seqNum) { _slowStartLastACK = seqNum; }
private:
void stopSlowStart(); // stops the slow start on loss or timeout
p_high_resolution_clock::time_point _lastRCTime = p_high_resolution_clock::now(); // last rate increase time
bool _slowStart { true }; // if in slow start phase
SequenceNumber _slowStartLastAck; // last ACKed seq num
SequenceNumber _slowStartLastACK; // last ACKed seq num from previous slow start check
bool _loss { false }; // if loss happened since last rate increase
SequenceNumber _lastDecreaseMaxSeq; // max pkt seq num sent out when last decrease happened
double _lastDecreasePeriod { 1 }; // value of _packetSendPeriod when last decrease happened

View file

@ -104,6 +104,9 @@ SendQueue& Connection::getSendQueue() {
_sendQueue->setSyncInterval(_synInterval);
_sendQueue->setEstimatedTimeout(estimatedTimeout());
_sendQueue->setFlowWindowSize(std::min(_flowWindowSize, (int) _congestionControl->_congestionWindowSize));
// give the randomized sequence number to the congestion control object
_congestionControl->setInitialSendSequenceNumber(_sendQueue->getCurrentSequenceNumber());
}
return *_sendQueue;
@ -282,7 +285,7 @@ void Connection::sendACK(bool wasCausedBySyncTimeout) {
// grab the up to date packet receive speed and estimated bandwidth
int32_t packetReceiveSpeed = _receiveWindow.getPacketReceiveSpeed();
int32_t estimatedBandwidth = _receiveWindow.getEstimatedBandwidth();
// update those values in our connection stats
_stats.recordReceiveRate(packetReceiveSpeed);
_stats.recordEstimatedBandwidth(estimatedBandwidth);
@ -541,7 +544,7 @@ void Connection::processACK(std::unique_ptr<ControlPacket> controlPacket) {
// read the ACK sub-sequence number
SequenceNumber currentACKSubSequenceNumber;
controlPacket->readPrimitive(&currentACKSubSequenceNumber);
// Check if we need send an ACK2 for this ACK
// This will be the case if it has been longer than the sync interval OR
// it looks like they haven't received our ACK2 for this ACK

View file

@ -21,12 +21,10 @@ in vec3 _normal;
in vec2 _texCoord0;
const float gamma = 2.2;
const float smoothing = 256.0;
const float smoothing = 32.0;
const float interiorCutoff = 0.8;
const float outlineExpansion = 0.2;
void main() {
// retrieve signed distance
float sdf = texture(Font, _texCoord0).g;

View file

@ -240,7 +240,9 @@ public:
const Varying getInput() const { return _input; }
const Varying getOutput() const { return _output; }
Model(const Varying& input, Data data = Data()) : Concept(std::make_shared<C>()), _data(data), _input(input), _output(Output()) {
template <class... A>
Model(const Varying& input, A&&... args) :
Concept(std::make_shared<C>()), _data(Data(std::forward<A>(args)...)), _input(input), _output(Output()) {
applyConfiguration();
}
@ -308,7 +310,10 @@ public:
const Varying getInput() const { return _input; }
const Varying getOutput() const { return _output; }
Model(const Varying& input, Data data = Data()) : Concept(data._config), _data(data), _input(input), _output(Output()) {
template <class... A>
Model(const Varying& input, A&&... args) :
Concept(nullptr), _data(Data(std::forward<A>(args)...)), _input(input), _output(Output()) {
_config = _data._config;
std::static_pointer_cast<Config>(_config)->init(&_data);
applyConfiguration();
}
@ -337,9 +342,7 @@ public:
// Create a new job in the container's queue; returns the job's output
template <class T, class... A> const Varying addJob(std::string name, const Varying& input, A&&... args) {
_jobs.emplace_back(name, std::make_shared<typename T::JobModel>(
input,
typename T::JobModel::Data(std::forward<A>(args)...)));
_jobs.emplace_back(name, std::make_shared<typename T::JobModel>(input, std::forward<A>(args)...));
QConfigPointer config = _jobs.back().getConfiguration();
config->setParent(_config.get());
config->setObjectName(name.c_str());