diff --git a/.travis.yml b/.travis.yml
index 73a40d0761a7b442cd2435b7ac37a59f5c13a875..890fcfd3ac3ca6f4d4ac9507586110c817dc3edf 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -5,4 +5,6 @@ before_install:
   - curl -o- -L https://yarnpkg.com/install.sh | bash -s -- --version 1.5.1
   - export PATH="$HOME/.yarn/bin:$PATH"
 install: yarn 
-script: yarn lint
+script:
+- yarn lint
+- ./scripts/check-yarn-lock.sh
diff --git a/package.json b/package.json
index 173823aca710f4d58bcfedb3787de67b2d025918..ad584f83bcf0827ec6c4f2914bf9e38abc20234b 100644
--- a/package.json
+++ b/package.json
@@ -24,7 +24,8 @@
     "aframe-extras": "^4.0.0",
     "aframe-input-mapping-component": "https://github.com/johnshaughnessy/aframe-input-mapping-component#feature/map-to-array",
     "aframe-physics-extras": "https://github.com/infinitelee/aframe-physics-extras#fix/physics-collider-crash",
-    "aframe-physics-system": "https://github.com/donmccurdy/aframe-physics-system",
+    "aframe-physics-system": "https://github.com/infinitelee/aframe-physics-system#feature/shape-component",
+    "aframe-rounded": "^1.0.3",
     "aframe-teleport-controls": "^0.3.1",
     "aframe-xr": "github:brianpeiris/aframe-xr#3162aed",
     "classnames": "^2.2.5",
@@ -35,7 +36,7 @@
     "mobile-detect": "^1.4.1",
     "moving-average": "^1.0.0",
     "naf-janus-adapter": "https://github.com/mozilla/naf-janus-adapter#feature/disconnect",
-    "networked-aframe": "github:mozillareality/networked-aframe#feature/sound-source-set",
+    "networked-aframe": "github:mozillareality/networked-aframe#mr-social-client/master",
     "nipplejs": "^0.6.7",
     "query-string": "^5.0.1",
     "raven-js": "^3.20.1",
@@ -74,6 +75,7 @@
     "rimraf": "^2.6.2",
     "sass-loader": "^6.0.7",
     "selfsigned": "^1.10.2",
+    "shelljs": "^0.8.1",
     "style-loader": "^0.20.2",
     "webpack": "^4.0.1",
     "webpack-cli": "^2.0.9",
diff --git a/scripts/check-yarn-lock.sh b/scripts/check-yarn-lock.sh
new file mode 100755
index 0000000000000000000000000000000000000000..e27b56ab47bc9746933266a02f0c30b7a7b9c6e1
--- /dev/null
+++ b/scripts/check-yarn-lock.sh
@@ -0,0 +1,10 @@
+#!/usr/bin/env bash
+
+if [ `git diff yarn.lock | wc -l` -ne 0 ]; then
+  echo ""
+  tput setaf 1
+  echo "!! UNCOMMITED YARN.LOCK CHANGES !!"
+  tput sgr0
+  echo ""
+  exit 1
+fi
diff --git a/src/assets/hud/avatar.png b/src/assets/hud/avatar.png
new file mode 100644
index 0000000000000000000000000000000000000000..d604f8f18d51b481bcc0013f30e2c610100b231c
Binary files /dev/null and b/src/assets/hud/avatar.png differ
diff --git a/src/assets/interactables/duck/DuckyMesh.glb b/src/assets/interactables/duck/DuckyMesh.glb
index 5bb10e0cd79c623f72f87d438f6eddbe1d0dc250..f50dc37942d519c36e16a5e41bb8a44a18c4c7f1 100644
Binary files a/src/assets/interactables/duck/DuckyMesh.glb and b/src/assets/interactables/duck/DuckyMesh.glb differ
diff --git a/src/assets/interactables/duck/gltf/DuckyMesh.fbm/Ducky.jpg b/src/assets/interactables/duck/gltf/DuckyMesh.fbm/Ducky.jpg
new file mode 100644
index 0000000000000000000000000000000000000000..6c27845f40d1e4b91ddb5534c413f408580ed51e
Binary files /dev/null and b/src/assets/interactables/duck/gltf/DuckyMesh.fbm/Ducky.jpg differ
diff --git a/src/assets/interactables/duck/gltf/DuckyMesh.gltf b/src/assets/interactables/duck/gltf/DuckyMesh.gltf
new file mode 100644
index 0000000000000000000000000000000000000000..83cc03646480c7cec3849fda0a8fd3580cec3abc
--- /dev/null
+++ b/src/assets/interactables/duck/gltf/DuckyMesh.gltf
@@ -0,0 +1,248 @@
+{
+  "asset": {
+    "generator": "FBX2glTF",
+    "version": "2.0"
+  },
+  "scene": 0,
+  "buffers": [
+    {
+      "byteLength": 18600,
+      "uri": "buffer.bin"
+    }
+  ],
+  "bufferViews": [
+    {
+      "buffer": 0,
+      "byteLength": 3336,
+      "byteOffset": 0,
+      "target": 34963
+    },
+    {
+      "buffer": 0,
+      "byteLength": 5724,
+      "byteOffset": 3336,
+      "target": 34962
+    },
+    {
+      "buffer": 0,
+      "byteLength": 5724,
+      "byteOffset": 9060,
+      "target": 34962
+    },
+    {
+      "buffer": 0,
+      "byteLength": 3816,
+      "byteOffset": 14784,
+      "target": 34962
+    }
+  ],
+  "scenes": [
+    {
+      "name": "Root Scene",
+      "nodes": [
+        0
+      ],
+      "extras": {
+        "components": {
+          "shape": [
+            {
+              "shape": "box",
+              "halfExtents": {
+                "x": 0.06,
+                "y": 0.04,
+                "z": 0.08
+              },
+              "offset": {
+                "x": 0,
+                "y": 0.052671334114334445,
+                "z": 0.01001389278835843
+              },
+              "orientation": {
+                "x": 0,
+                "y": 0,
+                "z": 0,
+                "w": 1
+              }
+            },
+            {
+              "shape": "sphere",
+              "radius": 0.05,
+              "offset": {
+                "x": 0,
+                "y": 0.1287570519589527,
+                "z": 0.033095376412929145
+              },
+              "orientation": {
+                "x": 0,
+                "y": 0,
+                "z": 0,
+                "w": 1
+              }
+            },
+            {
+              "shape": "cylinder",
+              "radiusTop": 0.02,
+              "radiusBottom": 0.02,
+              "height": 0.030000000000000013,
+              "numSegments": 8,
+              "offset": {
+                "x": 0,
+                "y": 0.12657048237702667,
+                "z": 0.09010837508332667
+              },
+              "orientation": {
+                "x": 0.7071067811865476,
+                "y": 0,
+                "z": 0,
+                "w": 0.7071067811865475
+              }
+            }
+          ]
+        }
+      }
+    }
+  ],
+  "accessors": [
+    {
+      "componentType": 5123,
+      "type": "SCALAR",
+      "count": 1668,
+      "bufferView": 0,
+      "byteOffset": 0
+    },
+    {
+      "componentType": 5126,
+      "type": "VEC3",
+      "count": 477,
+      "bufferView": 1,
+      "byteOffset": 0,
+      "min": [
+        -0.0587991699576378,
+        0.0129461474716663,
+        -0.0740185976028442
+      ],
+      "max": [
+        0.0618169121444225,
+        0.173104390501976,
+        0.104356855154037
+      ]
+    },
+    {
+      "componentType": 5126,
+      "type": "VEC3",
+      "count": 477,
+      "bufferView": 2,
+      "byteOffset": 0
+    },
+    {
+      "componentType": 5126,
+      "type": "VEC2",
+      "count": 477,
+      "bufferView": 3,
+      "byteOffset": 0
+    }
+  ],
+  "images": [
+    {
+      "name": "DuckyMesh.fbm/Ducky.jpg",
+      "uri": "DuckyMesh.fbm/Ducky.jpg"
+    }
+  ],
+  "samplers": [
+    {}
+  ],
+  "textures": [
+    {
+      "name": "file4",
+      "sampler": 0,
+      "source": 0
+    }
+  ],
+  "materials": [
+    {
+      "name": "lambert2",
+      "alphaMode": "OPAQUE",
+      "extras": {
+        "fromFBX": {
+          "shadingModel": "Lambert",
+          "isTruePBR": false
+        }
+      },
+      "pbrMetallicRoughness": {
+        "baseColorTexture": {
+          "index": 0,
+          "texCoord": 0
+        },
+        "baseColorFactor": [
+          0.800000011920929,
+          0.800000011920929,
+          0.800000011920929,
+          1
+        ],
+        "metallicFactor": 0.200000002980232,
+        "roughnessFactor": 0.800000011920929
+      }
+    }
+  ],
+  "meshes": [
+    {
+      "name": "Ducky",
+      "primitives": [
+        {
+          "material": 0,
+          "mode": 4,
+          "attributes": {
+            "NORMAL": 2,
+            "POSITION": 1,
+            "TEXCOORD_0": 3
+          },
+          "indices": 0
+        }
+      ]
+    }
+  ],
+  "nodes": [
+    {
+      "name": "RootNode",
+      "translation": [
+        0,
+        0,
+        0
+      ],
+      "rotation": [
+        0,
+        0,
+        0,
+        1
+      ],
+      "scale": [
+        1,
+        1,
+        1
+      ],
+      "children": [
+        1
+      ]
+    },
+    {
+      "name": "Ducky",
+      "translation": [
+        0,
+        0,
+        0
+      ],
+      "rotation": [
+        0,
+        0,
+        0,
+        1
+      ],
+      "scale": [
+        1,
+        1,
+        1
+      ],
+      "mesh": 0
+    }
+  ]
+}
\ No newline at end of file
diff --git a/src/assets/interactables/duck/gltf/DuckyMesh.json b/src/assets/interactables/duck/gltf/DuckyMesh.json
new file mode 100644
index 0000000000000000000000000000000000000000..97b41944a2ca7e12e5e12cf4892d2534ef73e5b4
--- /dev/null
+++ b/src/assets/interactables/duck/gltf/DuckyMesh.json
@@ -0,0 +1,60 @@
+{
+  "scenes": {
+    "Root Scene": {
+      "shape": [
+        {
+          "shape": "box",
+          "halfExtents": {
+            "x": 0.06,
+            "y": 0.04,
+            "z": 0.08
+          },
+          "offset": {
+            "x": 0,
+            "y": 0.052671334114334445,
+            "z": 0.01001389278835843
+          },
+          "orientation": {
+            "x": 0,
+            "y": 0,
+            "z": 0,
+            "w": 1
+          }
+        },
+        {
+          "shape": "sphere",
+          "radius": 0.05,
+          "offset": {
+            "x": 0,
+            "y": 0.1287570519589527,
+            "z": 0.033095376412929145
+          },
+          "orientation": {
+            "x": 0,
+            "y": 0,
+            "z": 0,
+            "w": 1
+          }
+        },
+        {
+          "shape": "cylinder",
+          "radiusTop": 0.02,
+          "radiusBottom": 0.02,
+          "height": 0.030000000000000013,
+          "numSegments": 8,
+          "offset": {
+            "x": 0,
+            "y": 0.12657048237702667,
+            "z": 0.09010837508332667
+          },
+          "orientation": {
+            "x": 0.7071067811865476,
+            "y": 0,
+            "z": 0,
+            "w": 0.7071067811865475
+          }
+        }
+      ]
+    }
+  }
+}
diff --git a/src/assets/interactables/duck/gltf/buffer.bin b/src/assets/interactables/duck/gltf/buffer.bin
new file mode 100644
index 0000000000000000000000000000000000000000..d7ed323e11aef0c4b2045dd8f2ddd34154244b84
Binary files /dev/null and b/src/assets/interactables/duck/gltf/buffer.bin differ
diff --git a/src/assets/stylesheets/2d-hud.css b/src/assets/stylesheets/2d-hud.css
index a8324a5bb8b054c4da44f82aadfe96647c5cb45b..a50436114181d18997248dce77a3cc1d9500363f 100644
--- a/src/assets/stylesheets/2d-hud.css
+++ b/src/assets/stylesheets/2d-hud.css
@@ -3,12 +3,45 @@
   top: 10px;
   display: flex;
   justify-content: center;
-  height: 60px;
+  align-items: center;
+  height: 80px;
   width: 100%;
 }
 
-:local(.bg) {
-  position: absolute;
+:local(.panel) {
+  display: flex;
+  justify-content: space-around;
+  align-items: center;
+  padding: 10px;
+  background-color: rgba(0, 0, 0, 0.35);
+}
+
+:local(.panel.left) {
+  border-bottom-left-radius: 30px;
+  border-top-left-radius: 30px;
+  padding-left: 20px;
+  padding-right: 50px;
+  margin-right: -40px;
+}
+
+:local(.panel.right) {
+  border-bottom-right-radius: 30px;
+  border-top-right-radius: 30px;
+  padding-right: 20px;
+  padding-left: 50px;
+  margin-left: -40px;
+}
+
+:local(.modeButton) {
+  width: 80px;
+  height: 80px;
+  display: flex;
+  align-items: center;
+  justify-content: center;
+  z-index: 10;
+}
+
+:local(.panel) {
   display: flex;
   justify-content: space-around;
   align-items: center;
@@ -16,6 +49,7 @@
   background-color: rgba(0, 0, 0, 0.35);
 }
 
+
 :local(.nametag) {
   display: flex;
   justify-content: center;
@@ -26,21 +60,20 @@
 }
 
 :local(.avatar) {
-  display: flex;
-  width: 48px;
-  height: 48px;
+  width: 80px;
+  height: 80px;
   background-size: 100%;
-  background-image: url(../hud/avatar.jpg);
+  background-image: url(../hud/avatar.png);
 }
 
 :local(.mic) {
   display: flex;
-  width: 48px;
-  height: 48px;
+  width: 32px;
+  height: 32px;
   -webkit-mask: url(../hud/unmuted.png);
-  -webkit-mask-size: 48px;
+  -webkit-mask-size: 32px;
   mask: url(../hud/unmuted.png);
-  mask-size: 48px;
+  mask-size: 32px;
   background-color: white;
   cursor: pointer;
 }
@@ -59,9 +92,9 @@
 
 :local(.mic.muted) {
   -webkit-mask: url(../hud/muted.png);
-  -webkit-mask-size: 48px;
+  -webkit-mask-size: 32px;
   mask: url(../hud/muted.png);
-  mask-size: 48px;
+  mask-size: 32px;
 }
 
 :local(.mic.muted:active) {
diff --git a/src/behaviours/oculus-touch-joystick-dpad4.js b/src/behaviours/joystick-dpad4.js
similarity index 86%
rename from src/behaviours/oculus-touch-joystick-dpad4.js
rename to src/behaviours/joystick-dpad4.js
index bf397ba2fbda2357c7fdf1cfc0310c8aa1ba548c..d0cc1e2a87d1882346deb724d5ba14570d46b02c 100644
--- a/src/behaviours/oculus-touch-joystick-dpad4.js
+++ b/src/behaviours/joystick-dpad4.js
@@ -1,7 +1,7 @@
 import { angleTo4Direction } from "../utils/dpad";
 
 // @TODO specify 4 or 8 direction
-function oculus_touch_joystick_dpad4(el, outputPrefix) {
+function joystick_dpad4(el, outputPrefix) {
   this.angleToDirection = angleTo4Direction;
   this.outputPrefix = outputPrefix;
   this.centerRadius = 0.6;
@@ -11,7 +11,7 @@ function oculus_touch_joystick_dpad4(el, outputPrefix) {
   el.addEventListener("axismove", this.emitDPad4);
 }
 
-oculus_touch_joystick_dpad4.prototype = {
+joystick_dpad4.prototype = {
   emitDPad4: function(event) {
     const x = event.detail.axis[0];
     const y = event.detail.axis[1];
@@ -25,4 +25,4 @@ oculus_touch_joystick_dpad4.prototype = {
   }
 };
 
-export { oculus_touch_joystick_dpad4 };
+export default joystick_dpad4;
diff --git a/src/behaviours/vive-trackpad-dpad4.js b/src/behaviours/trackpad-dpad4.js
similarity index 93%
rename from src/behaviours/vive-trackpad-dpad4.js
rename to src/behaviours/trackpad-dpad4.js
index 99bdf8873d4cbcce3541691e6073af71c153db2b..b23ca1dbdb1f61ec6d99e9d2fab17ab4c96b0248 100644
--- a/src/behaviours/vive-trackpad-dpad4.js
+++ b/src/behaviours/trackpad-dpad4.js
@@ -1,6 +1,6 @@
 import { angleTo4Direction } from "../utils/dpad";
 
-function vive_trackpad_dpad4(el, outputPrefix) {
+function trackpad_dpad4(el, outputPrefix) {
   this.outputPrefix = outputPrefix;
   this.lastDirection = "";
   this.previous = "";
@@ -15,7 +15,7 @@ function vive_trackpad_dpad4(el, outputPrefix) {
   el.addEventListener("trackpadup", this.unpress);
 }
 
-vive_trackpad_dpad4.prototype = {
+trackpad_dpad4.prototype = {
   press: function() {
     this.pressed = true;
   },
@@ -51,4 +51,4 @@ vive_trackpad_dpad4.prototype = {
   }
 };
 
-export { vive_trackpad_dpad4 };
+export default trackpad_dpad4;
diff --git a/src/components/hud-controller.js b/src/components/hud-controller.js
new file mode 100644
index 0000000000000000000000000000000000000000..4ee274f34ae9daa6f24c8e414eee824b845c49db
--- /dev/null
+++ b/src/components/hud-controller.js
@@ -0,0 +1,77 @@
+import { AppModes } from "../systems/app-mode.js";
+
+const TWOPI = Math.PI * 2;
+function deltaAngle(a, b) {
+  const p = Math.abs(b - a) % TWOPI;
+  return p > Math.PI ? TWOPI - p : p;
+}
+
+/**
+ * Positions the HUD and toggles app mode based on where the user is looking
+ */
+AFRAME.registerComponent("hud-controller", {
+  schema: {
+    head: { type: "selector" },
+    offset: { default: 0.7 }, // distance from hud above head,
+    lookCutoff: { default: 20 }, // angle at which the hud should be "on",
+    animRange: { default: 30 }, // degrees over which to animate the hud into view
+    yawCutoff: { default: 50 } // yaw degrees at wich the hud should reoirent even if the user is looking up
+  },
+  init() {
+    this.isYLocked = false;
+    this.lockedHeadPositionY = 0;
+  },
+
+  pause() {
+    // TODO: this assumes full control over current app mode reguardless of what else might be manipulating it, this is obviously wrong
+    const AppModeSystem = this.el.sceneEl.systems["app-mode"];
+    AppModeSystem.setMode(AppModes.DEFAULT);
+  },
+
+  tick() {
+    const hud = this.el.object3D;
+    const head = this.data.head.object3D;
+    const sceneEl = this.el.sceneEl;
+
+    const { offset, lookCutoff, animRange, yawCutoff } = this.data;
+
+    const pitch = head.rotation.x * THREE.Math.RAD2DEG;
+    const yawDif = deltaAngle(head.rotation.y, hud.rotation.y) * THREE.Math.RAD2DEG;
+
+    // Reorient the hud only if the user is looking away from the hud, for right now this arbitrarily means the hud is 1/3 way animated away
+    // TODO: come up with better huristics for this that maybe account for the user turning away from the hud "too far", also animate the position so that it doesnt just snap.
+    if (yawDif >= yawCutoff || pitch < lookCutoff - animRange / 3) {
+      const lookDir = new THREE.Vector3(0, 0, -1);
+      lookDir.applyQuaternion(head.quaternion);
+      lookDir.add(head.position);
+      hud.position.x = lookDir.x;
+      hud.position.z = lookDir.z;
+      hud.setRotationFromEuler(new THREE.Euler(0, head.rotation.y, 0));
+    }
+
+    // animate the hud into place over animRange degrees as the user aproaches the lookCutoff angle
+    const t = 1 - THREE.Math.clamp(lookCutoff - pitch, 0, animRange) / animRange;
+
+    // Lock the hud in place relative to a known head position so it doesn't bob up and down
+    // with the user's head
+    if (!this.isYLocked && t === 1) {
+      this.lockedHeadPositionY = head.position.y;
+    }
+    const EPSILON = 0.001;
+    this.isYLocked = t > 1 - EPSILON;
+
+    hud.position.y = (this.isYLocked ? this.lockedHeadPositionY : head.position.y) + offset + (1 - t) * offset;
+    hud.rotation.x = (1 - t) * THREE.Math.DEG2RAD * 90;
+
+    // update the app mode when the HUD locks on or off
+    // TODO: this assumes full control over current app mode reguardless of what else might be manipulating it, this is obviously wrong
+    const AppModeSystem = sceneEl.systems["app-mode"];
+    if (pitch > lookCutoff && AppModeSystem.mode !== AppModes.HUD) {
+      AppModeSystem.setMode(AppModes.HUD);
+      sceneEl.renderer.sortObjects = true;
+    } else if (pitch < lookCutoff && AppModeSystem.mode === AppModes.HUD) {
+      AppModeSystem.setMode(AppModes.DEFAULT);
+      sceneEl.renderer.sortObjects = false;
+    }
+  }
+});
diff --git a/src/components/in-world-hud.js b/src/components/in-world-hud.js
index aa7e8aae756207dc05a640f7d02f6c0f728b41ca..9e307e498256da344e5e2e3533baf82b09f93b6f 100644
--- a/src/components/in-world-hud.js
+++ b/src/components/in-world-hud.js
@@ -4,29 +4,11 @@ AFRAME.registerComponent("in-world-hud", {
     raycaster: { type: "selector" }
   },
   init() {
-    this.bg = this.el.querySelector(".bg");
     this.mic = this.el.querySelector(".mic");
-    this.nametag = this.el.querySelector(".username");
-    this.avatar = this.el.querySelector(".avatar");
-    this.nametag.object3DMap.text.material.depthTest = false;
-    this.nametag.object3DMap.text.renderOrder = 1;
-    this.mic.object3DMap.mesh.renderOrder = 1;
-    this.avatar.object3DMap.mesh.renderOrder = 1;
-
-    const line = this.data.raycaster.object3DMap.line;
-    line.renderOrder = 2;
-    line.material.depthTest = false;
-    // Set opacity to 0.99 to force the line to render in the
-    // transparent pass, so that it renders on top of the HUD
-    this.data.raycaster.setAttribute("line", "opacity", 0.99);
 
     const muted = this.el.sceneEl.is("muted");
     this.mic.setAttribute("src", muted ? "#muted" : "#unmuted");
 
-    const scene = this.el.sceneEl;
-    this.onUsernameChanged = this.onUsernameChanged.bind(this);
-    scene.addEventListener("username-changed", this.onUsernameChanged);
-
     this.showCorrectMuteState = () => {
       const muted = this.el.sceneEl.is("muted");
       this.mic.setAttribute("src", muted ? "#muted" : "#unmuted");
@@ -95,9 +77,6 @@ AFRAME.registerComponent("in-world-hud", {
   },
 
   pause() {
-    this.nametag.removeEventListener("raycaster-intersected", this.onNametagHovered);
-    this.nametag.removeEventListener("raycaster-intersected-cleared", this.onNametagUnhovered);
-
     this.el.sceneEl.removeEventListener("stateadded", this.onStateChange);
     this.el.sceneEl.removeEventListener("stateremoved", this.onStateChange);
 
@@ -120,12 +99,5 @@ AFRAME.registerComponent("in-world-hud", {
       volume: this.volume,
       levels: this.levels
     });
-  },
-
-  onUsernameChanged(evt) {
-    const { username } = evt.detail;
-    const width = evt.detail.username.length == 0 ? 1 : 40 / username.length;
-    this.nametag.setAttribute("text", "width", Math.min(width, 6));
-    this.nametag.setAttribute("text", "value", username);
   }
 });
diff --git a/src/components/nav-mesh-helper.js b/src/components/nav-mesh-helper.js
new file mode 100644
index 0000000000000000000000000000000000000000..5c1be4ce96946dddb6ba98590dc7da27d403ab10
--- /dev/null
+++ b/src/components/nav-mesh-helper.js
@@ -0,0 +1,16 @@
+AFRAME.registerComponent("nav-mesh-helper", {
+  schema: {
+    teleportControls: { type: "selectorAll", default: "[teleport-controls]" }
+  },
+
+  init: function() {
+    const teleportControls = this.data.teleportControls;
+    this.el.addEventListener("bundleloaded", () => {
+      if (!teleportControls) return;
+
+      for (let i = 0; i < teleportControls.length; i++) {
+        teleportControls[i].components["teleport-controls"].queryCollisionEntities();
+      }
+    });
+  }
+});
diff --git a/src/components/super-cursor.js b/src/components/super-cursor.js
index b8daee493abcbfb543db553538c5b968748da381..ee70e960663144709f17108d70a2378a6bc9f935 100644
--- a/src/components/super-cursor.js
+++ b/src/components/super-cursor.js
@@ -92,7 +92,7 @@ AFRAME.registerComponent("super-cursor", {
       this.data.cursor.object3D.position.copy(this.point);
     }
 
-    this.isInteractable = intersection && intersection.object.el.className === "interactable";
+    this.isInteractable = intersection && this._isInteractable(intersection.object.el);
 
     if ((this.isGrabbing || this.isInteractable) && !this.wasIntersecting) {
       this.wasIntersecting = true;
@@ -103,6 +103,13 @@ AFRAME.registerComponent("super-cursor", {
     }
   },
 
+  _isInteractable: function(el) {
+    return (
+      el.className === "interactable" ||
+      (el.parentNode && el.parentNode != el.sceneEl && this._isInteractable(el.parentNode))
+    );
+  },
+
   _handleMouseDown: function() {
     if (this.isInteractable) {
       const lookControls = this.data.camera.components["look-controls"];
@@ -122,7 +129,19 @@ AFRAME.registerComponent("super-cursor", {
   },
 
   _handleWheel: function(e) {
-    if (this.isGrabbing) this.currentDistanceMod += e.deltaY / 10;
+    if (this.isGrabbing) {
+      switch (e.deltaMode) {
+        case e.DOM_DELTA_PIXEL:
+          this.currentDistanceMod += e.deltaY / 500;
+          break;
+        case e.DOM_DELTA_LINE:
+          this.currentDistanceMod += e.deltaY / 10;
+          break;
+        case e.DOM_DELTA_PAGE:
+          this.currentDistanceMod += e.deltaY / 2;
+          break;
+      }
+    }
   },
 
   _handleEnterVR: function() {
diff --git a/src/gltf-component-mappings.js b/src/gltf-component-mappings.js
index 06e81969a0f72d0d3a90ae7b247f28bf68fa2aaa..2166e7a62a186c9caa1ce3da8f39b5cafa4fff31 100644
--- a/src/gltf-component-mappings.js
+++ b/src/gltf-component-mappings.js
@@ -2,5 +2,6 @@ import "./components/gltf-model-plus";
 
 AFRAME.GLTFModelPlus.registerComponent("scale-audio-feedback", "scale-audio-feedback");
 AFRAME.GLTFModelPlus.registerComponent("loop-animation", "loop-animation");
+AFRAME.GLTFModelPlus.registerComponent("shape", "shape");
 AFRAME.GLTFModelPlus.registerComponent("visible", "visible");
 AFRAME.GLTFModelPlus.registerComponent("nav-mesh", "nav-mesh");
diff --git a/src/hub.html b/src/hub.html
index b1f063732df95a6da2da232a209ccdffc465d4bd..9892cdcf01e840af3d78a69d2417e1c20b5fabe1 100644
--- a/src/hub.html
+++ b/src/hub.html
@@ -29,7 +29,7 @@
         <a-assets>
             <img id="unmuted"  src="./assets/hud/unmuted.png" >
             <img id="muted"  src="./assets/hud/muted.png" >
-            <img id="avatar"  src="./assets/hud/avatar.jpg" >
+            <img id="avatar"  src="./assets/hud/avatar.png" >
 
             <a-asset-item id="botdefault" response-type="arraybuffer" src="https://asset-bundles-prod.reticulum.io/bots/BotDefault_Avatar-9f71f8ff22.gltf"></a-asset-item>
             <a-asset-item id="botbobo" response-type="arraybuffer" src="https://asset-bundles-prod.reticulum.io/bots/BotBobo_Avatar-f9740a010b.gltf"></a-asset-item>
@@ -105,11 +105,11 @@
 
             <template id="interactable-template">
                 <a-entity
-                    gltf-model-plus="src: #interactable-duck"
+                    gltf-model-plus="src: #interactable-duck; inflate: true;"
                     scale="2 2 2"
                     class="interactable" 
                     super-networked-interactable="counter: #counter; mass: 5;"
-                    body="type: dynamic; mass: 5; shape: box;"
+                    body="type: dynamic; shape: none; mass: 5;"
                     grabbable
                     stretchable="useWorldPosition: true;"
                 ></a-entity>
@@ -173,11 +173,11 @@
                 vr-mode-toggle-visibility
                 vr-mode-toggle-playing__hud-controller
             >
-                <a-entity in-world-hud="haptic:#player-right-controller;raycaster:#player-right-controller;" rotation="-39 0 0">
-                    <a-box geometry="height:0.13;width:0.6;depth:0.001" material="depthTest:false; color:#000000;opacity:0.35" class="hud bg"></a-box>
-                    <a-image src="#unmuted" scale="-0.1 0.1 0.1" position="-0.2 0 0.001" class="hud mic" material="alphaTest:0.1;depthTest:false;"></a-image>
-                    <a-text scale="0.3 0.3 0.3" position="0 0 0.001" class="hud username" text="width:6;alphaTest:0.1;align:center;"></a-text>
-                    <a-image src="#avatar" scale="0.1 0.1 0.1" position="0.2 0 0.001" class="hud avatar" material="depthTest:false;"></a-image>
+                <a-entity in-world-hud="haptic:#player-right-controller;raycaster:#player-right-controller;" rotation="30 0 0">
+                    <a-rounded height="0.13" width="0.6" color="#000000" position="-0.3 -0.065 0" radius="0.065" opacity="0.35" class="hud bg"></a-rounded>
+                    <a-image src="#unmuted" scale="0.1 0.1 0.1" position="-0.2 0 0.001" class="hud mic" material="alphaTest:0.1;"></a-image>
+                    <a-image src="#avatar" scale="0.2 0.2 0.2" position="0 0 0.001" class="hud avatar"></a-image>
+                    <a-image src="#unmuted" scale="0.1 0.1 0.1" position="0.2 0 0.001" class="hud mic" material="alphaTest:0.1;"></a-image>
                 </a-entity>
             </a-entity>
 
@@ -203,8 +203,6 @@
                 haptic-feedback
             ></a-entity>
 
-
-
             <a-entity
                 id="player-right-controller"
                 class="right-controller"
@@ -280,7 +278,7 @@
         ></a-entity>
 
         <!-- Environment -->
-        <a-entity id="environment-root" position="0 0 0"></a-entity>
+        <a-entity id="environment-root" position="0 0 0" nav-mesh-helper></a-entity>
 
         <a-entity
             id="skybox"
diff --git a/src/hub.js b/src/hub.js
index 1a1c08b453a285a9d95a1c1b8d5ad40b17980ed0..9f2c8ffd8901d091b1108ef3ba6838f4d5c7e6d7 100644
--- a/src/hub.js
+++ b/src/hub.js
@@ -11,10 +11,11 @@ import "naf-janus-adapter";
 import "aframe-teleport-controls";
 import "aframe-input-mapping-component";
 import "aframe-billboard-component";
+import "aframe-rounded";
 import "webrtc-adapter";
 
-import { vive_trackpad_dpad4 } from "./behaviours/vive-trackpad-dpad4";
-import { oculus_touch_joystick_dpad4 } from "./behaviours/oculus-touch-joystick-dpad4";
+import trackpad_dpad4 from "./behaviours/trackpad-dpad4";
+import { joystick_dpad4 } from "./behaviours/joystick-dpad4";
 import { PressedMove } from "./activators/pressedmove";
 import { ReverseY } from "./activators/reversey";
 import "./activators/shortpress";
@@ -44,6 +45,7 @@ import "./components/loop-animation";
 import "./components/hand-poses";
 import "./components/gltf-model-plus";
 import "./components/gltf-bundle";
+import "./components/hud-controller";
 
 import ReactDOM from "react-dom";
 import React from "react";
@@ -77,6 +79,8 @@ import "./components/super-spawner";
 import "./components/super-cursor";
 import "./components/event-repeater";
 
+import "./components/nav-mesh-helper";
+
 import registerNetworkSchemas from "./network-schemas";
 import { inGameActions, config as inputConfig } from "./input-mappings";
 import registerTelemetry from "./telemetry";
@@ -94,8 +98,8 @@ function qsTruthy(param) {
 
 registerTelemetry();
 
-AFRAME.registerInputBehaviour("vive_trackpad_dpad4", vive_trackpad_dpad4);
-AFRAME.registerInputBehaviour("oculus_touch_joystick_dpad4", oculus_touch_joystick_dpad4);
+AFRAME.registerInputBehaviour("trackpad_dpad4", trackpad_dpad4);
+AFRAME.registerInputBehaviour("joystick_dpad4", joystick_dpad4);
 AFRAME.registerInputActivator("pressedmove", PressedMove);
 AFRAME.registerInputActivator("reverseY", ReverseY);
 AFRAME.registerInputMappings(inputConfig, true);
diff --git a/src/input-mappings.js b/src/input-mappings.js
index 035110dd677efa748c280ae0d6b8f14fde1ae6f4..9296fd71ffa9f31c32308cff00cd7d4bd3096dcf 100644
--- a/src/input-mappings.js
+++ b/src/input-mappings.js
@@ -21,29 +21,37 @@ const config = {
   behaviours: {
     default: {
       "oculus-touch-controls": {
-        joystick: "oculus_touch_joystick_dpad4"
+        joystick: "joystick_dpad4"
       },
       "vive-controls": {
-        trackpad: "vive_trackpad_dpad4"
+        trackpad: "trackpad_dpad4"
+      },
+      "daydream-controls": {
+        trackpad: "trackpad_dpad4"
+      },
+      "gearvr-controls": {
+        trackpad: "trackpad_dpad4"
       }
     }
   },
   mappings: {
     default: {
       "vive-controls": {
-        menudown: ["action_mute", "thumb_down"],
-        menuup: "thumb_up",
         "trackpad.pressedmove": { left: "move" },
         trackpad_dpad4_pressed_west_down: { right: "snap_rotate_left" },
         trackpad_dpad4_pressed_east_down: { right: "snap_rotate_right" },
         trackpad_dpad4_pressed_center_down: { right: "action_teleport_down" },
+        trackpad_dpad4_pressed_north_down: { right: "action_teleport_down" },
+        trackpad_dpad4_pressed_south_down: { right: "action_teleport_down" },
         trackpadup: { right: "action_teleport_up" },
+        menudown: "thumb_down",
+        menuup: "thumb_up",
         gripdown: ["action_grab", "middle_ring_pinky_down", "index_down"],
         gripup: ["action_release", "middle_ring_pinky_up", "index_up"],
         trackpadtouchstart: "thumb_down",
         trackpadtouchend: "thumb_up",
-        triggerdown: "index_down",
-        triggerup: "index_up"
+        triggerdown: ["action_grab", "index_down"],
+        triggerup: ["action_release", "index_up"]
       },
       "oculus-touch-controls": {
         joystick_dpad4_west: {
@@ -52,7 +60,6 @@ const config = {
         joystick_dpad4_east: {
           right: "snap_rotate_right"
         },
-        xbuttondown: "action_mute",
         gripdown: ["action_grab", "middle_ring_pinky_down"],
         gripup: ["action_release", "middle_ring_pinky_up"],
         abuttontouchstart: "thumb_down",
@@ -67,20 +74,26 @@ const config = {
         surfacetouchend: "thumb_up",
         thumbsticktouchstart: "thumb_down",
         thumbsticktouchend: "thumb_up",
-        triggerdown: ["action_teleport_down", "index_down"],
-        triggerup: ["action_teleport_up", "index_up"],
+        triggerdown: "index_down",
+        triggerup: "index_up",
         "axismove.reverseY": { left: "move" },
-        right_dpad_east: "snap_rotate_right",
-        right_dpad_west: "snap_rotate_left",
         abuttondown: "action_teleport_down",
         abuttonup: "action_teleport_up"
       },
       "daydream-controls": {
-        trackpaddown: "action_teleport_down",
+        trackpad_dpad4_pressed_west_down: "snap_rotate_left",
+        trackpad_dpad4_pressed_east_down: "snap_rotate_right",
+        trackpad_dpad4_pressed_center_down: "action_teleport_down",
+        trackpad_dpad4_pressed_north_down: "action_teleport_down",
+        trackpad_dpad4_pressed_south_down: "action_teleport_down",
         trackpadup: "action_teleport_up"
       },
       "gearvr-controls": {
-        trackpaddown: "action_teleport_down",
+        trackpad_dpad4_pressed_west_down: "snap_rotate_left",
+        trackpad_dpad4_pressed_east_down: "snap_rotate_right",
+        trackpad_dpad4_pressed_center_down: "action_teleport_down",
+        trackpad_dpad4_pressed_north_down: "action_teleport_down",
+        trackpad_dpad4_pressed_south_down: "action_teleport_down",
         trackpadup: "action_teleport_up"
       },
       keyboard: {
@@ -100,14 +113,14 @@ const config = {
         s_up: "s_up",
         d_down: "d_down",
         d_up: "d_up",
-        W_down: "w_down",
-        W_up: "w_up",
-        A_down: "a_down",
-        A_up: "a_up",
-        S_down: "s_down",
-        S_up: "s_up",
-        D_down: "d_down",
-        D_up: "d_up"
+        arrowup_down: "w_down",
+        arrowup_up: "w_up",
+        arrowleft_down: "a_down",
+        arrowleft_up: "a_up",
+        arrowdown_down: "s_down",
+        arrowdown_up: "s_up",
+        arrowright_down: "d_down",
+        arrowright_up: "d_up"
       }
     },
     hud: {
@@ -116,8 +129,8 @@ const config = {
         triggerup: { right: "action_ui_select_up" }
       },
       "oculus-touch-controls": {
-        triggerdown: { right: "action_ui_select_down" },
-        triggerup: { right: "action_ui_select_up" },
+        abuttondown: "action_ui_select_down",
+        abuttonup: "action_ui_select_up",
         gripdown: "middle_ring_pinky_down",
         gripup: "middle_ring_pinky_up",
         abuttontouchstart: "thumb_down",
diff --git a/src/react-components/2d-hud.js b/src/react-components/2d-hud.js
index 8d9223a072c97c670210e67e48434cfc58543d49..9679bb9c090af49966c6f5cbf03072201c860f00 100644
--- a/src/react-components/2d-hud.js
+++ b/src/react-components/2d-hud.js
@@ -4,18 +4,21 @@ import cx from "classnames";
 
 import styles from "../assets/stylesheets/2d-hud.css";
 
-const TwoDHUD = ({ name, muted, onToggleMute }) => (
+const TwoDHUD = ({ muted, onToggleMute }) => (
   <div className={styles.container}>
-    <div className={cx("ui-interactive", styles.bg)}>
+    <div className={cx("ui-interactive", styles.panel, styles.left)}>
       <div className={cx(styles.mic, { [styles.muted]: muted })} onClick={onToggleMute} />
-      <div className={styles.nametag}>{name}</div>
+    </div>
+    <div className={cx("ui-interactive", styles.modeButton)}>
       <div className={styles.avatar} />
     </div>
+    <div className={cx("ui-interactive", styles.panel, styles.right)}>
+      <div className={cx(styles.mic, { [styles.muted]: muted })} onClick={onToggleMute} />
+    </div>
   </div>
 );
 
 TwoDHUD.propTypes = {
-  name: PropTypes.string,
   muted: PropTypes.bool,
   onToggleMute: PropTypes.func
 };
diff --git a/src/react-components/ui-root.js b/src/react-components/ui-root.js
index 3970a2305c4439900b4936f8e465d2d0039a8de0..282f4b4572156fb4e757616a1e8c02e19df34727 100644
--- a/src/react-components/ui-root.js
+++ b/src/react-components/ui-root.js
@@ -737,11 +737,7 @@ class UIRoot extends Component {
             )}
           </div>
           {this.state.entryStep === ENTRY_STEPS.finished ? (
-            <TwoDHUD
-              name={this.props.store.state.profile.display_name}
-              muted={this.state.muted}
-              onToggleMute={this.toggleMute}
-            />
+            <TwoDHUD muted={this.state.muted} onToggleMute={this.toggleMute} />
           ) : null}
         </div>
       </IntlProvider>
diff --git a/src/systems/app-mode.js b/src/systems/app-mode.js
index 1ef1c2cd0d7b79c75d0738717558901370320e5b..49e8d361bd90de4612fe4548fc0ecb4cc027d53d 100644
--- a/src/systems/app-mode.js
+++ b/src/systems/app-mode.js
@@ -1,6 +1,6 @@
 /* global AFRAME, console, setTimeout, clearTimeout */
 
-const AppModes = Object.freeze({ DEFAULT: "default", HUD: "hud" });
+export const AppModes = Object.freeze({ DEFAULT: "default", HUD: "hud" });
 
 /**
  * Simple system for keeping track of a modal app state
@@ -89,82 +89,6 @@ AFRAME.registerComponent("app-mode-input-mappings", {
   }
 });
 
-const TWOPI = Math.PI * 2;
-function deltaAngle(a, b) {
-  const p = Math.abs(b - a) % TWOPI;
-  return p > Math.PI ? TWOPI - p : p;
-}
-
-/**
- * Positions the HUD and toggles app mode based on where the user is looking
- */
-AFRAME.registerComponent("hud-controller", {
-  schema: {
-    head: { type: "selector" },
-    offset: { default: 1 }, // distance from hud below head,
-    lookCutoff: { default: -25 }, // angle at which the hud should be "on",
-    animRange: { default: 30 }, // degrees over which to animate the hud into view
-    yawCutoff: { default: 100 } // yaw degrees at wich the hud should reoirent even if the user is looking down
-  },
-  init() {
-    this.isYLocked = false;
-    this.lockedHeadPositionY = 0;
-  },
-
-  pause() {
-    // TODO: this assumes full control over current app mode reguardless of what else might be manipulating it, this is obviously wrong
-    const AppModeSystem = this.el.sceneEl.systems["app-mode"];
-    AppModeSystem.setMode(AppModes.DEFAULT);
-  },
-
-  tick() {
-    const hud = this.el.object3D;
-    const head = this.data.head.object3D;
-    const sceneEl = this.el.sceneEl;
-
-    const { offset, lookCutoff, animRange, yawCutoff } = this.data;
-
-    const pitch = head.rotation.x * THREE.Math.RAD2DEG;
-    const yawDif = deltaAngle(head.rotation.y, hud.rotation.y) * THREE.Math.RAD2DEG;
-
-    // Reorient the hud only if the user is looking "up", for right now this arbitrarily means the hud is 1/3 way animated away
-    // TODO: come up with better huristics for this that maybe account for the user turning away from the hud "too far", also animate the position so that it doesnt just snap.
-    if (yawDif >= yawCutoff || pitch > lookCutoff + animRange / 3) {
-      const lookDir = new THREE.Vector3(0, 0, -1);
-      lookDir.applyQuaternion(head.quaternion);
-      lookDir.add(head.position);
-      hud.position.x = lookDir.x;
-      hud.position.z = lookDir.z;
-      hud.setRotationFromEuler(new THREE.Euler(0, head.rotation.y, 0));
-    }
-
-    //animate the hud into place over animRange degrees as the user aproaches the lookCutoff angle
-    const t = 1 - THREE.Math.clamp(pitch - lookCutoff, 0, animRange) / animRange;
-
-    // Lock the hud in place relative to a known head position so it doesn't bob up and down
-    // with the user's head
-    if (!this.isYLocked && t === 1) {
-      this.lockedHeadPositionY = head.position.y;
-    }
-    const EPSILON = 0.001;
-    this.isYLocked = t > 1 - EPSILON;
-
-    hud.position.y = (this.isYLocked ? this.lockedHeadPositionY : head.position.y) - offset - offset * (1 - t);
-    hud.rotation.x = (1 - t) * THREE.Math.DEG2RAD * 90;
-
-    // update the app mode when the HUD locks on or off
-    // TODO: this assumes full control over current app mode reguardless of what else might be manipulating it, this is obviously wrong
-    const AppModeSystem = sceneEl.systems["app-mode"];
-    if (pitch < lookCutoff && AppModeSystem.mode !== AppModes.HUD) {
-      AppModeSystem.setMode(AppModes.HUD);
-      sceneEl.renderer.sortObjects = true;
-    } else if (pitch > lookCutoff && AppModeSystem.mode === AppModes.HUD) {
-      AppModeSystem.setMode(AppModes.DEFAULT);
-      sceneEl.renderer.sortObjects = false;
-    }
-  }
-});
-
 /**
  * Toggle visibility of an entity based on if the user is in vr mode or not
  */
diff --git a/yarn.lock b/yarn.lock
index 352623872827845ef84e0f8c46f3535945602f45..9e4e6fbae46ef483424f8b4ada1dadce72744951 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -170,19 +170,13 @@ aframe-extras@^4.0.0:
   version "0.1.2"
   resolved "https://github.com/johnshaughnessy/aframe-input-mapping-component#4c7e493ad6c4a25eef27d32551c94d8b78541191"
 
-aframe-lerp-component@^1.1.0:
-  version "1.1.0"
-  resolved "https://registry.yarnpkg.com/aframe-lerp-component/-/aframe-lerp-component-1.1.0.tgz#dc8c12c53698770c30f25eef8873e34a4e79c765"
-  dependencies:
-    almost-equal "^1.1.0"
-
 "aframe-physics-extras@https://github.com/infinitelee/aframe-physics-extras#fix/physics-collider-crash":
   version "0.1.2"
   resolved "https://github.com/infinitelee/aframe-physics-extras#49b2d5d3c0caac905783aee51d9e89dbdf7199b8"
 
-"aframe-physics-system@https://github.com/donmccurdy/aframe-physics-system":
-  version "3.0.1"
-  resolved "https://github.com/donmccurdy/aframe-physics-system#08a98a4c3d77c4c38a1fa27067aa0d894447902e"
+"aframe-physics-system@https://github.com/infinitelee/aframe-physics-system#feature/shape-component":
+  version "3.0.2"
+  resolved "https://github.com/infinitelee/aframe-physics-system#be3e43f1af5b995952e1b3d27dce216ab2e79f05"
   dependencies:
     browserify "^14.3.0"
     budo "^10.0.3"
@@ -190,6 +184,10 @@ aframe-lerp-component@^1.1.0:
     three-to-cannon "^1.2.0"
     webworkify "^1.4.0"
 
+aframe-rounded@^1.0.3:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/aframe-rounded/-/aframe-rounded-1.0.3.tgz#72c7d9c0ff02e94ee138bf217c284e187efa3cfb"
+
 aframe-teleport-controls@^0.3.1:
   version "0.3.1"
   resolved "https://registry.yarnpkg.com/aframe-teleport-controls/-/aframe-teleport-controls-0.3.1.tgz#7d7ef206f483ea92425a6333b0f8fb26c9596d1c"
@@ -230,10 +228,6 @@ ajv@^6.0.1, ajv@^6.1.0:
     fast-json-stable-stringify "^2.0.0"
     json-schema-traverse "^0.3.0"
 
-almost-equal@^1.1.0:
-  version "1.1.0"
-  resolved "https://registry.yarnpkg.com/almost-equal/-/almost-equal-1.1.0.tgz#f851c631138757994276aa2efbe8dfa3066cccdd"
-
 alphanum-sort@^1.0.1, alphanum-sort@^1.0.2:
   version "1.0.2"
   resolved "https://registry.yarnpkg.com/alphanum-sort/-/alphanum-sort-1.0.2.tgz#97a1119649b211ad33691d9f9f486a8ec9fbe0a3"
@@ -5351,11 +5345,10 @@ neo-async@^2.5.0:
   version "2.5.0"
   resolved "https://registry.yarnpkg.com/neo-async/-/neo-async-2.5.0.tgz#76b1c823130cca26acfbaccc8fbaf0a2fa33b18f"
 
-"networked-aframe@github:mozillareality/networked-aframe#feature/sound-source-set":
-  version "0.6.0"
-  resolved "https://codeload.github.com/mozillareality/networked-aframe/tar.gz/978b7c25aff26a0c1db47beb35d8a6556f717d36"
+"networked-aframe@github:mozillareality/networked-aframe#mr-social-client/master":
+  version "0.6.1"
+  resolved "https://codeload.github.com/mozillareality/networked-aframe/tar.gz/69be0e7e5f66070526c8240cb795b9e88da971a9"
   dependencies:
-    aframe-lerp-component "^1.1.0"
     easyrtc "1.1.0"
     express "^4.10.7"
     serve-static "^1.8.0"
@@ -7202,6 +7195,14 @@ shelljs@^0.7.0:
     interpret "^1.0.0"
     rechoir "^0.6.2"
 
+shelljs@^0.8.1:
+  version "0.8.1"
+  resolved "https://registry.yarnpkg.com/shelljs/-/shelljs-0.8.1.tgz#729e038c413a2254c4078b95ed46e0397154a9f1"
+  dependencies:
+    glob "^7.0.0"
+    interpret "^1.0.0"
+    rechoir "^0.6.2"
+
 sigmund@~1.0.0:
   version "1.0.1"
   resolved "https://registry.yarnpkg.com/sigmund/-/sigmund-1.0.1.tgz#3ff21f198cad2175f9f3b781853fd94d0d19b590"