Merge branch 'master' of https://github.com/highfidelity/hifi into ignore_penumbra

This commit is contained in:
Atlante45 2014-11-05 15:42:50 +01:00
commit 617bb23206
38 changed files with 465 additions and 332 deletions

View file

@ -1109,6 +1109,14 @@ void DomainServer::sendHeartbeatToDataServer(const QString& networkAddress) {
domainObject[AUTOMATIC_NETWORKING_KEY] = _automaticNetworkingSetting;
// add a flag to indicate if this domain uses restricted access - for now that will exclude it from listings
const QString RESTRICTED_ACCESS_FLAG = "restricted";
const QVariant* allowedUsersVariant = valueForKeyPath(_settingsManager.getSettingsMap(),
ALLOWED_USERS_SETTINGS_KEYPATH);
QStringList allowedUsers = allowedUsersVariant ? allowedUsersVariant->toStringList() : QStringList();
domainObject[RESTRICTED_ACCESS_FLAG] = (allowedUsers.size() > 0);
// add the number of currently connected agent users
int numConnectedAuthedUsers = 0;
foreach(const SharedNodePointer& node, LimitedNodeList::getInstance()->getNodeHash()) {
@ -1140,7 +1148,7 @@ void DomainServer::performICEUpdates() {
}
void DomainServer::sendHeartbeatToIceServer() {
const HifiSockAddr ICE_SERVER_SOCK_ADDR = HifiSockAddr("ice.highfidelity.io", ICE_SERVER_DEFAULT_PORT);
static HifiSockAddr ICE_SERVER_SOCK_ADDR = HifiSockAddr("ice.highfidelity.io", ICE_SERVER_DEFAULT_PORT);
LimitedNodeList::getInstance()->sendHeartbeatToIceServer(ICE_SERVER_SOCK_ADDR);
}

View file

@ -0,0 +1,50 @@
//
// audioMuteExample.js
// examples
//
// Created by Thijs Wenker on 10/31/14.
// Copyright 2014 High Fidelity, Inc.
//
// This example shows how to use the AudioDevice mute functions.
// Press the MUTE/UNMUTE button to see it function.
//
// Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
//
var toggleMuteButton = Overlays.addOverlay("text", {
x: 50,
y: 50,
width: 190,
height: 50,
backgroundColor: { red: 255, green: 255, blue: 255},
color: { red: 255, green: 0, blue: 0},
font: {size: 30},
topMargin: 10
});
function muteButtonText() {
print("Audio Muted: " + AudioDevice.getMuted());
}
function onMuteStateChanged() {
Overlays.editOverlay(toggleMuteButton,
AudioDevice.getMuted() ? {text: "UNMUTE", leftMargin: 10} : {text: "MUTE", leftMargin: 38});
print("Audio Muted: " + AudioDevice.getMuted());
}
function mousePressEvent(event) {
if (Overlays.getOverlayAtPoint({x: event.x, y: event.y}) == toggleMuteButton) {
AudioDevice.toggleMute()
}
}
function scriptEnding() {
Overlays.deleteOverlay(toggleMuteButton);
}
onMuteStateChanged();
AudioDevice.muteToggled.connect(onMuteStateChanged);
Controller.mousePressEvent.connect(mousePressEvent);
Script.scriptEnding.connect(scriptEnding);

View file

@ -23,7 +23,7 @@ var THRUST_CONTROLLER = 0;
var VIEW_CONTROLLER = 1;
function checkCamera(deltaTime) {
if (Camera.getMode() == "independent") {
if (Camera.mode == "independent") {
var THRUST_MAG_UP = 800.0;
var THRUST_MAG_DOWN = 300.0;
var THRUST_MAG_FWD = 500.0;
@ -102,19 +102,19 @@ function keyPressEvent(event) {
}
if (event.text == "1") {
Camera.setMode("first person");
Camera.mode = "first person";
}
if (event.text == "2") {
Camera.setMode("mirror");
Camera.mode = "mirror";
}
if (event.text == "3") {
Camera.setMode("third person");
Camera.mode = "third person";
}
if (event.text == "4") {
Camera.setMode("independent");
Camera.mode = "independent";
joysticksCaptured = true;
Controller.captureJoystick(THRUST_CONTROLLER);
Controller.captureJoystick(VIEW_CONTROLLER);

View file

@ -20,15 +20,15 @@ var cameraLocations = [ {x: 7971.9, y: 241.3, z: 7304.1}, {x: 7973.0, y: 241.3,
var cameraLookAts = [ {x: 7971.1, y: 241.3, z: 7304.1}, {x: 7972.1, y: 241.3, z: 7304.1}, {x: 7972.1, y: 241.3, z: 7304.1}, {x: 7972.1, y: 241.3, z: 7304.1}, {x: 7972.1, y: 241.3, z: 7304.1}, {x: 7971.3, y: 241.3, z: 7304.2} ];
function saveCameraState() {
oldMode = Camera.getMode();
oldMode = Camera.mode;
avatarPosition = MyAvatar.position;
Camera.setModeShiftPeriod(0.0);
Camera.setMode("independent");
Camera.mode = "independent";
}
function restoreCameraState() {
Camera.stopLooking();
Camera.setMode(oldMode);
Camera.mode = oldMode;
}
function update(deltaTime) {
@ -52,7 +52,7 @@ function keyPressEvent(event) {
saveCameraState();
freeCamera = true;
}
Camera.setMode("independent");
Camera.mode = "independent";
Camera.setPosition(cameraLocations[choice - 1]);
Camera.keepLookingAt(cameraLookAts[choice - 1]);
}

View file

@ -20,15 +20,15 @@ var cameraLocations = [ {x: 8027.5, y: 237.5, z: 7305.7}, {x: 8027.5, y: 237.5,
var cameraLookAts = [ {x: 8027.5, y: 237.5, z: 7304.0}, {x: 8027.5, y: 237.5, z: 7305.7}, {x: 8027.5, y: 237.5, z: 7304.0}, {x: 8027.5, y: 237.5, z: 7304.0}, {x: 8027.5, y: 237.5, z: 7304.0}, {x: 8027.5, y: 237.5, z: 7304.0} ];
function saveCameraState() {
oldMode = Camera.getMode();
oldMode = Camera.mode;
avatarPosition = MyAvatar.position;
Camera.setModeShiftPeriod(0.0);
Camera.setMode("independent");
Camera.mode = "independent";
}
function restoreCameraState() {
Camera.stopLooking();
Camera.setMode(oldMode);
Camera.mode = oldMode;
}
function update(deltaTime) {
@ -52,7 +52,7 @@ function keyPressEvent(event) {
saveCameraState();
freeCamera = true;
}
Camera.setMode("independent");
Camera.mode = "independent";
Camera.setPosition(cameraLocations[choice - 1]);
Camera.keepLookingAt(cameraLookAts[choice - 1]);
}

View file

@ -20,15 +20,15 @@ var cameraLocations = [ {x: 2921.5, y: 251.3, z: 8254.8}, {x: 2921.5, y: 251.3,
var cameraLookAts = [ {x: 2921.5, y: 251.3, z: 8255.7}, {x: 2921.5, y: 251.3, z: 8255.7}, {x: 2921.5, y: 251.3, z: 8255.7}, {x: 2921.5, y: 251.3, z: 8255.7}, {x: 2921.4 , y: 251.3, z: 8255.1} ];
function saveCameraState() {
oldMode = Camera.getMode();
oldMode = Camera.mode;
avatarPosition = MyAvatar.position;
Camera.setModeShiftPeriod(0.0);
Camera.setMode("independent");
Camera.mode = "independent";
}
function restoreCameraState() {
Camera.stopLooking();
Camera.setMode(oldMode);
Camera.mode = oldMode;
}
function update(deltaTime) {
@ -52,7 +52,7 @@ function keyPressEvent(event) {
saveCameraState();
freeCamera = true;
}
Camera.setMode("independent");
Camera.mode = "independent";
Camera.setPosition(cameraLocations[choice - 1]);
Camera.keepLookingAt(cameraLookAts[choice - 1]);
}

View file

@ -50,14 +50,14 @@ var SPAWN_DISTANCE = 1;
var DEFAULT_DIMENSION = 0.20;
var modelURLs = [
HIFI_PUBLIC_BUCKET + "meshes/Feisar_Ship.FBX",
HIFI_PUBLIC_BUCKET + "meshes/birarda/birarda_head.fbx",
HIFI_PUBLIC_BUCKET + "meshes/pug.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Alder.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Bush1.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Bush6.fbx",
HIFI_PUBLIC_BUCKET + "meshes/newInvader16x16-large-purple.svo",
HIFI_PUBLIC_BUCKET + "meshes/minotaur/mino_full.fbx",
HIFI_PUBLIC_BUCKET + "meshes/Combat_tank_V01.FBX",
HIFI_PUBLIC_BUCKET + "meshes/orc.fbx",
HIFI_PUBLIC_BUCKET + "meshes/slimer.fbx"
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed2.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed4.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed7.fbx"
];
var jointList = MyAvatar.getJointNames();

View file

@ -53,12 +53,12 @@ var lastYawTurned = 0.0;
var startPullbackPosition;
function saveCameraState() {
oldMode = Camera.getMode();
Camera.setMode("independent");
oldMode = Camera.mode;
Camera.mode = "independent";
}
function restoreCameraState() {
Camera.setMode(oldMode);
Camera.mode = oldMode;
}
function activateWarp() {

View file

@ -118,14 +118,14 @@ function handlePanMode(dx, dy) {
}
function saveCameraState() {
oldMode = Camera.getMode();
oldMode = Camera.mode;
var oldPosition = Camera.getPosition();
Camera.setMode("independent");
Camera.mode = "independent";
Camera.setPosition(oldPosition);
}
function restoreCameraState() {
Camera.setMode(oldMode);
Camera.mode = oldMode;
}
function handleModes() {

View file

@ -34,6 +34,13 @@ var EASING_MULTIPLIER = 8;
var INITIAL_ZOOM_DISTANCE = 2;
var INITIAL_ZOOM_DISTANCE_FIRST_PERSON = 3;
var easeOutCubic = function(t) {
t--;
return t * t * t + 1;
};
EASE_TIME = 0.5;
CameraManager = function() {
var that = {};
@ -51,6 +58,10 @@ CameraManager = function() {
that.focalPoint = { x: 0, y: 0, z: 0 };
that.targetFocalPoint = { x: 0, y: 0, z: 0 };
easing = false;
easingTime = 0;
startOrientation = Quat.fromPitchYawRollDegrees(0, 0, 0);
that.previousCameraMode = null;
that.lastMousePosition = { x: 0, y: 0 };
@ -66,10 +77,6 @@ CameraManager = function() {
var focalPoint = Vec3.sum(Camera.getPosition(),
Vec3.multiply(that.zoomDistance, Quat.getFront(Camera.getOrientation())));
if (Camera.getMode() == 'first person') {
that.targetZoomDistance = INITIAL_ZOOM_DISTANCE_FIRST_PERSON;
}
// Determine the correct yaw and pitch to keep the camera in the same location
var dPos = Vec3.subtract(focalPoint, Camera.getPosition());
var xzDist = Math.sqrt(dPos.x * dPos.x + dPos.z * dPos.z);
@ -81,8 +88,8 @@ CameraManager = function() {
that.focalPoint = focalPoint;
that.setFocalPoint(focalPoint);
that.previousCameraMode = Camera.getMode();
Camera.setMode("independent");
that.previousCameraMode = Camera.mode;
Camera.mode = "independent";
that.updateCamera();
@ -95,18 +102,40 @@ CameraManager = function() {
that.mode = MODE_INACTIVE;
if (!ignoreCamera) {
Camera.setMode(that.previousCameraMode);
Camera.mode = that.previousCameraMode;
}
cameraTool.setVisible(false);
}
that.focus = function() {
var dim = SelectionManager.worldDimensions;
var size = Math.max(dim.x, Math.max(dim.y, dim.z));
that.focus = function(position, dimensions, easeOrientation) {
if (dimensions) {
var size = Math.max(dimensions.x, Math.max(dimensions.y, dimensions.z));
that.targetZoomDistance = Math.max(size * FOCUS_ZOOM_SCALE, FOCUS_MIN_ZOOM);
} else {
that.targetZoomDistance = Vec3.length(Vec3.subtract(Camera.getPosition(), position));
}
that.targetZoomDistance = Math.max(size * FOCUS_ZOOM_SCALE, FOCUS_MIN_ZOOM);
if (easeOrientation) {
// Do eased turning towards target
that.focalPoint = that.targetFocalPoint = position;
that.setFocalPoint(SelectionManager.worldPosition);
that.zoomDistance = that.targetZoomDistance = Vec3.length(Vec3.subtract(Camera.getPosition(), position));
var dPos = Vec3.subtract(that.focalPoint, Camera.getPosition());
var xzDist = Math.sqrt(dPos.x * dPos.x + dPos.z * dPos.z);
that.targetPitch = -Math.atan2(dPos.y, xzDist) * 180 / Math.PI;
that.targetYaw = Math.atan2(dPos.x, dPos.z) * 180 / Math.PI;
that.pitch = that.targetPitch;
that.yaw = that.targetYaw;
startOrientation = Camera.getOrientation();
easing = true;
easingTime = 0;
} else {
that.setFocalPoint(position);
}
that.updateCamera();
}
@ -242,7 +271,7 @@ CameraManager = function() {
}
that.updateCamera = function() {
if (!that.enabled || Camera.getMode() != "independent") return;
if (!that.enabled || Camera.mode != "independent") return;
var yRot = Quat.angleAxis(that.yaw, { x: 0, y: 1, z: 0 });
var xRot = Quat.angleAxis(that.pitch, { x: 1, y: 0, z: 0 });
@ -255,6 +284,11 @@ CameraManager = function() {
xRot = Quat.angleAxis(-that.pitch, { x: 1, y: 0, z: 0 });
q = Quat.multiply(yRot, xRot);
if (easing) {
var t = easeOutCubic(easingTime / EASE_TIME);
q = Quat.slerp(startOrientation, q, t);
}
Camera.setOrientation(q);
}
@ -266,10 +300,14 @@ CameraManager = function() {
// Ease the position and orbit of the camera
that.update = function(dt) {
if (Camera.getMode() != "independent") {
if (Camera.mode != "independent") {
return;
}
if (easing) {
easingTime = Math.min(EASE_TIME, easingTime + dt);
}
var scale = Math.min(dt * EASING_MULTIPLIER, 1.0);
var dYaw = that.targetYaw - that.yaw;
@ -292,12 +330,15 @@ CameraManager = function() {
that.zoomDistance += scale * dZoom;
that.updateCamera();
if (easingTime >= 1) {
easing = false;
}
}
// Last mode that was first or third person
var lastAvatarCameraMode = "first person";
Camera.modeUpdated.connect(function(newMode) {
print("Camera mode has been updated: " + newMode);
if (newMode == "first person" || newMode == "third person") {
lastAvatarCameraMode = newMode;
that.disable(true);
@ -308,7 +349,7 @@ CameraManager = function() {
Controller.keyReleaseEvent.connect(function (event) {
if (event.text == "ESC" && that.enabled) {
Camera.setMode(lastAvatarCameraMode);
Camera.mode = lastAvatarCameraMode;
cameraManager.disable(true);
}
});

View file

@ -40,20 +40,18 @@ var ORB_SHIFT = { x: 0, y: -1.4, z: -0.8};
var HELMET_ATTACHMENT_URL = "https://hifi-public.s3.amazonaws.com/models/attachments/IronManMaskOnly.fbx"
function reticlePosition() {
var screenSize = Controller.getViewportDimensions();
var reticleRay = Camera.computePickRay(screenSize.x / 2, screenSize.y / 2);
var RETICLE_DISTANCE = 1;
return Vec3.sum(reticleRay.origin, Vec3.multiply(reticleRay.direction, RETICLE_DISTANCE));
return Vec3.sum(Camera.position, Vec3.multiply(Quat.getFront(Camera.orientation), RETICLE_DISTANCE));
}
function drawLobby() {
if (!panelWall) {
print("Adding overlays for the lobby panel wall and orb shell.");
var cameraEuler = Quat.safeEulerAngles(Camera.getOrientation());
var cameraEuler = Quat.safeEulerAngles(Camera.orientation);
var towardsMe = Quat.angleAxis(cameraEuler.y + 180, { x: 0, y: 1, z: 0});
var orbPosition = Vec3.sum(Camera.getPosition(), Vec3.multiplyQbyV(towardsMe, ORB_SHIFT));
var orbPosition = Vec3.sum(Camera.position, Vec3.multiplyQbyV(towardsMe, ORB_SHIFT));
var panelWallProps = {
url: HIFI_PUBLIC_BUCKET + "models/sets/Lobby/LobbyPrototype/Lobby5_PanelsWithFrames.fbx",
@ -76,14 +74,15 @@ function drawLobby() {
orbShell = Overlays.addOverlay("model", orbShellProps);
// for HMD wearers, create a reticle in center of screen
var RETICLE_SPHERE_SIZE = 0.025;
var CURSOR_SCALE = 0.025;
reticle = Overlays.addOverlay("sphere", {
reticle = Overlays.addOverlay("billboard", {
url: HIFI_PUBLIC_BUCKET + "images/cursor.svg",
position: reticlePosition(),
size: RETICLE_SPHERE_SIZE,
color: { red: 0, green: 255, blue: 0 },
ignoreRayIntersection: true,
isFacingAvatar: true,
alpha: 1.0,
solid: true
scale: CURSOR_SCALE
});
// add an attachment on this avatar so other people see them in the lobby
@ -130,12 +129,13 @@ function cleanupLobby() {
function actionStartEvent(event) {
if (panelWall) {
// we've got an action event and our panel wall is up
// check if we hit a panel and if we should jump there
var pickRay = Camera.computePickRay(event.x, event.y);
var result = Overlays.findRayIntersection(pickRay);
var result = Overlays.findRayIntersection(event.actionRay);
if (result.intersects && result.overlayID == panelWall) {
var panelName = result.extraInfo;
var panelStringIndex = panelName.indexOf("Panel");
if (panelStringIndex != -1) {

View file

@ -17,13 +17,13 @@
//
var lookingAtSomething = false;
var oldMode = Camera.getMode();
var oldMode = Camera.mode;
function cancelLookAt() {
if (lookingAtSomething) {
lookingAtSomething = false;
Camera.stopLooking();
Camera.setMode(oldMode);
Camera.mode = oldMode;
releaseMovementKeys();
}
}
@ -65,13 +65,13 @@ function mousePressEvent(event) {
if (intersection.intersects) {
// remember the old mode we were in
oldMode = Camera.getMode();
oldMode = Camera.mode;
print("looking at intersection point: " + intersection.intersection.x + ", "
+ intersection.intersection.y + ", " + intersection.intersection.z);
// switch to independent mode
Camera.setMode("independent");
Camera.mode = "independent";
// tell the camera to fix it's look at on the point we clicked
Camera.keepLookingAt(intersection.intersection);

View file

@ -51,15 +51,21 @@ var wantEntityGlow = false;
var SPAWN_DISTANCE = 1;
var DEFAULT_DIMENSION = 0.20;
var MENU_INSPECT_TOOL_ENABLED = "Inspect Tool";
var MENU_EASE_ON_FOCUS = "Ease Orientation on Focus";
var SETTING_INSPECT_TOOL_ENABLED = "inspectToolEnabled";
var SETTING_EASE_ON_FOCUS = "cameraEaseOnFocus";
var modelURLs = [
HIFI_PUBLIC_BUCKET + "meshes/Feisar_Ship.FBX",
HIFI_PUBLIC_BUCKET + "meshes/birarda/birarda_head.fbx",
HIFI_PUBLIC_BUCKET + "meshes/pug.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Alder.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Bush1.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/2-Terrain:%20Bush6.fbx",
HIFI_PUBLIC_BUCKET + "meshes/newInvader16x16-large-purple.svo",
HIFI_PUBLIC_BUCKET + "meshes/minotaur/mino_full.fbx",
HIFI_PUBLIC_BUCKET + "meshes/Combat_tank_V01.FBX",
HIFI_PUBLIC_BUCKET + "meshes/orc.fbx",
HIFI_PUBLIC_BUCKET + "meshes/slimer.fbx"
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed2.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed4.fbx",
HIFI_PUBLIC_BUCKET + "models/entities/3-Buildings-1-Rustic-Shed7.fbx"
];
var mode = 0;
@ -387,7 +393,6 @@ function isLocked(properties) {
var selectedEntityID;
var mouseLastPosition;
var orientation;
var intersection;
@ -401,142 +406,158 @@ function rayPlaneIntersection(pickRay, point, normal) {
return Vec3.sum(pickRay.origin, Vec3.multiply(pickRay.direction, t));
}
function findClickedEntity(event) {
var pickRay = Camera.computePickRay(event.x, event.y);
var foundIntersection = Entities.findRayIntersection(pickRay);
if (!foundIntersection.accurate) {
return null;
}
var foundEntity = foundIntersection.entityID;
if (!foundEntity.isKnownID) {
var identify = Entities.identifyEntity(foundEntity);
if (!identify.isKnownID) {
print("Unknown ID " + identify.id + " (update loop " + foundEntity.id + ")");
selectionManager.clearSelections();
return null;
}
foundEntity = identify;
}
return { pickRay: pickRay, entityID: foundEntity };
}
function mousePressEvent(event) {
mouseLastPosition = { x: event.x, y: event.y };
var clickedOverlay = Overlays.getOverlayAtPoint({ x: event.x, y: event.y });
var entitySelected = false;
if (toolBar.mousePressEvent(event) || progressDialog.mousePressEvent(event)
|| cameraManager.mousePressEvent(event) || selectionDisplay.mousePressEvent(event)) {
// Event handled; do nothing.
if (toolBar.mousePressEvent(event) || progressDialog.mousePressEvent(event)) {
return;
} else {
// If we aren't active and didn't click on an overlay: quit
if (!isActive) {
}
if (isActive) {
var entitySelected = false;
if (cameraManager.mousePressEvent(event) || selectionDisplay.mousePressEvent(event)) {
// Event handled; do nothing.
return;
}
var pickRay = Camera.computePickRay(event.x, event.y);
Vec3.print("[Mouse] Looking at: ", pickRay.origin);
var foundIntersection = Entities.findRayIntersection(pickRay);
if(!foundIntersection.accurate) {
selectionManager.clearSelections();
return;
}
var foundEntity = foundIntersection.entityID;
if (!foundEntity.isKnownID) {
var identify = Entities.identifyEntity(foundEntity);
if (!identify.isKnownID) {
print("Unknown ID " + identify.id + " (update loop " + foundEntity.id + ")");
} else {
var result = findClickedEntity(event);
if (result === null) {
selectionManager.clearSelections();
return;
}
foundEntity = identify;
}
var pickRay = result.pickRay;
var foundEntity = result.entityID;
var properties = Entities.getEntityProperties(foundEntity);
if (isLocked(properties)) {
print("Model locked " + properties.id);
} else {
var halfDiagonal = Vec3.length(properties.dimensions) / 2.0;
var properties = Entities.getEntityProperties(foundEntity);
if (isLocked(properties)) {
print("Model locked " + properties.id);
} else {
var halfDiagonal = Vec3.length(properties.dimensions) / 2.0;
print("Checking properties: " + properties.id + " " + properties.isKnownID + " - Half Diagonal:" + halfDiagonal);
// P P - Model
// /| A - Palm
// / | d B - unit vector toward tip
// / | X - base of the perpendicular line
// A---X----->B d - distance fom axis
// x x - distance from A
//
// |X-A| = (P-A).B
// X == A + ((P-A).B)B
// d = |P-X|
print("Checking properties: " + properties.id + " " + properties.isKnownID + " - Half Diagonal:" + halfDiagonal);
// P P - Model
// /| A - Palm
// / | d B - unit vector toward tip
// / | X - base of the perpendicular line
// A---X----->B d - distance fom axis
// x x - distance from A
//
// |X-A| = (P-A).B
// X == A + ((P-A).B)B
// d = |P-X|
var A = pickRay.origin;
var B = Vec3.normalize(pickRay.direction);
var P = properties.position;
var A = pickRay.origin;
var B = Vec3.normalize(pickRay.direction);
var P = properties.position;
var x = Vec3.dot(Vec3.subtract(P, A), B);
var X = Vec3.sum(A, Vec3.multiply(B, x));
var d = Vec3.length(Vec3.subtract(P, X));
var halfDiagonal = Vec3.length(properties.dimensions) / 2.0;
var x = Vec3.dot(Vec3.subtract(P, A), B);
var X = Vec3.sum(A, Vec3.multiply(B, x));
var d = Vec3.length(Vec3.subtract(P, X));
var halfDiagonal = Vec3.length(properties.dimensions) / 2.0;
var angularSize = 2 * Math.atan(halfDiagonal / Vec3.distance(Camera.getPosition(), properties.position)) * 180 / 3.14;
var angularSize = 2 * Math.atan(halfDiagonal / Vec3.distance(Camera.getPosition(), properties.position)) * 180 / 3.14;
var sizeOK = (allowLargeModels || angularSize < MAX_ANGULAR_SIZE)
&& (allowSmallModels || angularSize > MIN_ANGULAR_SIZE);
var sizeOK = (allowLargeModels || angularSize < MAX_ANGULAR_SIZE)
&& (allowSmallModels || angularSize > MIN_ANGULAR_SIZE);
if (0 < x && sizeOK) {
entitySelected = true;
selectedEntityID = foundEntity;
orientation = MyAvatar.orientation;
intersection = rayPlaneIntersection(pickRay, P, Quat.getFront(orientation));
if (0 < x && sizeOK) {
entitySelected = true;
selectedEntityID = foundEntity;
orientation = MyAvatar.orientation;
intersection = rayPlaneIntersection(pickRay, P, Quat.getFront(orientation));
if (!event.isShifted) {
selectionManager.clearSelections();
if (!event.isShifted) {
selectionManager.clearSelections();
}
selectionManager.addEntity(foundEntity);
print("Model selected: " + foundEntity.id);
}
selectionManager.addEntity(foundEntity);
print("Model selected: " + foundEntity.id);
}
}
}
if (entitySelected) {
selectionDisplay.select(selectedEntityID, event);
if (entitySelected) {
selectionDisplay.select(selectedEntityID, event);
}
} else if (Menu.isOptionChecked(MENU_INSPECT_TOOL_ENABLED)) {
var result = findClickedEntity(event);
if (event.isRightButton) {
if (result !== null) {
var currentProperties = Entities.getEntityProperties(result.entityID);
cameraManager.enable();
cameraManager.focus(currentProperties.position, null, Menu.isOptionChecked(MENU_EASE_ON_FOCUS));
cameraManager.mousePressEvent(event);
}
} else {
cameraManager.mousePressEvent(event);
}
}
}
var highlightedEntityID = { isKnownID: false };
function mouseMoveEvent(event) {
if (!isActive) {
return;
}
// allow the selectionDisplay and cameraManager to handle the event first, if it doesn't handle it, then do our own thing
if (selectionDisplay.mouseMoveEvent(event) || cameraManager.mouseMoveEvent(event)) {
return;
}
var pickRay = Camera.computePickRay(event.x, event.y);
var entityIntersection = Entities.findRayIntersection(pickRay);
if (entityIntersection.accurate) {
if(highlightedEntityID.isKnownID && highlightedEntityID.id != entityIntersection.entityID.id) {
selectionDisplay.unhighlightSelectable(highlightedEntityID);
highlightedEntityID = { id: -1, isKnownID: false };
if (isActive) {
// allow the selectionDisplay and cameraManager to handle the event first, if it doesn't handle it, then do our own thing
if (selectionDisplay.mouseMoveEvent(event) || cameraManager.mouseMoveEvent(event)) {
return;
}
var halfDiagonal = Vec3.length(entityIntersection.properties.dimensions) / 2.0;
var angularSize = 2 * Math.atan(halfDiagonal / Vec3.distance(Camera.getPosition(),
entityIntersection.properties.position)) * 180 / 3.14;
var sizeOK = (allowLargeModels || angularSize < MAX_ANGULAR_SIZE)
&& (allowSmallModels || angularSize > MIN_ANGULAR_SIZE);
if (entityIntersection.entityID.isKnownID && sizeOK) {
if (wantEntityGlow) {
Entities.editEntity(entityIntersection.entityID, { glowLevel: 0.25 });
var pickRay = Camera.computePickRay(event.x, event.y);
var entityIntersection = Entities.findRayIntersection(pickRay);
if (entityIntersection.accurate) {
if(highlightedEntityID.isKnownID && highlightedEntityID.id != entityIntersection.entityID.id) {
selectionDisplay.unhighlightSelectable(highlightedEntityID);
highlightedEntityID = { id: -1, isKnownID: false };
}
highlightedEntityID = entityIntersection.entityID;
selectionDisplay.highlightSelectable(entityIntersection.entityID);
}
var halfDiagonal = Vec3.length(entityIntersection.properties.dimensions) / 2.0;
var angularSize = 2 * Math.atan(halfDiagonal / Vec3.distance(Camera.getPosition(),
entityIntersection.properties.position)) * 180 / 3.14;
var sizeOK = (allowLargeModels || angularSize < MAX_ANGULAR_SIZE)
&& (allowSmallModels || angularSize > MIN_ANGULAR_SIZE);
if (entityIntersection.entityID.isKnownID && sizeOK) {
if (wantEntityGlow) {
Entities.editEntity(entityIntersection.entityID, { glowLevel: 0.25 });
}
highlightedEntityID = entityIntersection.entityID;
selectionDisplay.highlightSelectable(entityIntersection.entityID);
}
}
} else {
cameraManager.mouseMoveEvent(event);
}
}
function mouseReleaseEvent(event) {
if (!isActive) {
return;
}
if (selectionManager.hasSelection()) {
if (isActive && selectionManager.hasSelection()) {
tooltip.show(false);
}
cameraManager.mouseReleaseEvent(event);
}
@ -575,6 +596,11 @@ function setupModelMenus() {
Menu.addMenuItem({ menuName: "File", menuItemName: "Export Models", shortcutKey: "CTRL+META+E", afterItem: "Models" });
Menu.addMenuItem({ menuName: "File", menuItemName: "Import Models", shortcutKey: "CTRL+META+I", afterItem: "Export Models" });
Menu.addMenuItem({ menuName: "Developer", menuItemName: "Debug Ryans Rotation Problems", isCheckable: true });
Menu.addMenuItem({ menuName: "View", menuItemName: MENU_INSPECT_TOOL_ENABLED, afterItem: "Edit Entities Help...",
isCheckable: true, isChecked: Settings.getValue(SETTING_INSPECT_TOOL_ENABLED) == "true" });
Menu.addMenuItem({ menuName: "View", menuItemName: MENU_EASE_ON_FOCUS, afterItem: MENU_INSPECT_TOOL_ENABLED,
isCheckable: true, isChecked: Settings.getValue(SETTING_EASE_ON_FOCUS) == "true" });
}
setupModelMenus(); // do this when first running our script.
@ -596,9 +622,15 @@ function cleanupModelMenus() {
Menu.removeMenuItem("File", "Export Models");
Menu.removeMenuItem("File", "Import Models");
Menu.removeMenuItem("Developer", "Debug Ryans Rotation Problems");
Menu.removeMenuItem("View", MENU_INSPECT_TOOL_ENABLED);
Menu.removeMenuItem("View", MENU_EASE_ON_FOCUS);
}
Script.scriptEnding.connect(function() {
Settings.setValue(SETTING_INSPECT_TOOL_ENABLED, Menu.isOptionChecked(MENU_INSPECT_TOOL_ENABLED));
Settings.setValue(SETTING_EASE_ON_FOCUS, Menu.isOptionChecked(MENU_EASE_ON_FOCUS));
progressDialog.cleanup();
toolBar.cleanup();
cleanupModelMenus();
@ -718,7 +750,11 @@ Controller.keyReleaseEvent.connect(function (event) {
} else if (event.text == "TAB") {
selectionDisplay.toggleSpaceMode();
} else if (event.text == "f") {
cameraManager.focus();
if (isActive) {
cameraManager.focus(selectionManager.worldPosition,
selectionManager.worldDimensions,
Menu.isOptionChecked(MENU_EASE_ON_FOCUS));
}
} else if (event.text == '[') {
if (isActive) {
cameraManager.enable();
@ -796,7 +832,6 @@ function applyEntityProperties(data) {
var properties = data.createEntities[i].properties;
var newEntityID = Entities.addEntity(properties);
DELETED_ENTITY_MAP[entityID.id] = newEntityID;
print(newEntityID.isKnownID);
if (data.selectCreated) {
selectedEntityIDs.push(newEntityID);
}

View file

@ -14,9 +14,6 @@
// the depth texture
uniform sampler2D depthTexture;
// the normal texture
uniform sampler2D normalTexture;
// the random rotation texture
uniform sampler2D rotationTexture;
@ -60,11 +57,10 @@ vec3 texCoordToViewSpace(vec2 texCoord) {
}
void main(void) {
vec3 rotationZ = texture2D(normalTexture, gl_TexCoord[0].st).xyz * 2.0 - vec3(1.0, 1.0, 1.0);
vec3 rotationY = normalize(cross(rotationZ, texture2D(rotationTexture,
gl_TexCoord[0].st * noiseScale).xyz - vec3(0.5, 0.5, 0.5)));
mat3 rotation = mat3(cross(rotationY, rotationZ), rotationY, rotationZ);
vec3 rotationX = texture2D(rotationTexture, gl_TexCoord[0].st * noiseScale).rgb;
vec3 rotationY = normalize(cross(rotationX, vec3(0.0, 0.0, 1.0)));
mat3 rotation = mat3(rotationX, rotationY, cross(rotationX, rotationY));
vec3 center = texCoordToViewSpace(gl_TexCoord[0].st);
vec2 rdenominator = 1.0 / (rightTop - leftBottom);

View file

@ -620,8 +620,8 @@ void Application::paintGL() {
} else if (_myCamera.getMode() == CAMERA_MODE_THIRD_PERSON) {
static const float THIRD_PERSON_CAMERA_DISTANCE = 1.5f;
_myCamera.setPosition(_myAvatar->getUprightHeadPosition() +
_myAvatar->getOrientation() * glm::vec3(0.0f, 0.0f, 1.0f) * THIRD_PERSON_CAMERA_DISTANCE * _myAvatar->getScale());
_myCamera.setPosition(_myAvatar->getDefaultEyePosition() +
_myAvatar->getOrientation() * glm::vec3(0.0f, 0.0f, 1.0f) * THIRD_PERSON_CAMERA_DISTANCE * _myAvatar->getScale());
if (OculusManager::isConnected()) {
_myCamera.setRotation(_myAvatar->getWorldAlignedOrientation());
} else {
@ -1116,7 +1116,8 @@ void Application::keyPressEvent(QKeyEvent* event) {
case Qt::Key_Space: {
if (!event->isAutoRepeat()) {
// this starts an HFActionEvent
HFActionEvent startActionEvent(HFActionEvent::startType(), getViewportCenter());
HFActionEvent startActionEvent(HFActionEvent::startType(),
_viewFrustum.computePickRay(0.5f, 0.5f));
sendEvent(this, &startActionEvent);
}
@ -1207,7 +1208,7 @@ void Application::keyReleaseEvent(QKeyEvent* event) {
case Qt::Key_Space: {
if (!event->isAutoRepeat()) {
// this ends the HFActionEvent
HFActionEvent endActionEvent(HFActionEvent::endType(), getViewportCenter());
HFActionEvent endActionEvent(HFActionEvent::endType(), _viewFrustum.computePickRay(0.5f, 0.5f));
sendEvent(this, &endActionEvent);
}
@ -1301,7 +1302,8 @@ void Application::mousePressEvent(QMouseEvent* event, unsigned int deviceID) {
}
// nobody handled this - make it an action event on the _window object
HFActionEvent actionEvent(HFActionEvent::startType(), event->localPos());
HFActionEvent actionEvent(HFActionEvent::startType(),
_myCamera.computePickRay(event->x(), event->y()));
sendEvent(this, &actionEvent);
} else if (event->button() == Qt::RightButton) {
@ -1335,7 +1337,8 @@ void Application::mouseReleaseEvent(QMouseEvent* event, unsigned int deviceID) {
}
// fire an action end event
HFActionEvent actionEvent(HFActionEvent::endType(), event->localPos());
HFActionEvent actionEvent(HFActionEvent::endType(),
_myCamera.computePickRay(event->x(), event->y()));
sendEvent(this, &actionEvent);
}
}
@ -1977,6 +1980,9 @@ void Application::init() {
connect(getAudio(), &Audio::preProcessOriginalInboundAudio, &_audioReflector,
&AudioReflector::preProcessOriginalInboundAudio,Qt::DirectConnection);
connect(getAudio(), &Audio::muteToggled, AudioDeviceScriptingInterface::getInstance(),
&AudioDeviceScriptingInterface::muteToggled, Qt::DirectConnection);
// save settings when avatar changes
connect(_myAvatar, &MyAvatar::transformChanged, this, &Application::bumpSettings);
}
@ -3846,9 +3852,7 @@ void Application::registerScriptEngineWithApplicationServices(ScriptEngine* scri
scriptEngine->setAvatarData(_myAvatar, "MyAvatar"); // leave it as a MyAvatar class to expose thrust features
scriptEngine->setAvatarHashMap(&_avatarManager, "AvatarList");
CameraScriptableObject* cameraScriptable = new CameraScriptableObject(&_myCamera, &_viewFrustum);
scriptEngine->registerGlobalObject("Camera", cameraScriptable);
connect(scriptEngine, SIGNAL(finished(const QString&)), cameraScriptable, SLOT(deleteLater()));
scriptEngine->registerGlobalObject("Camera", &_myCamera);
#if defined(Q_OS_MAC) || defined(Q_OS_WIN)
scriptEngine->registerGlobalObject("SpeechRecognizer", Menu::getInstance()->getSpeechRecognizer());

View file

@ -287,8 +287,6 @@ public:
PointShader& getPointShader() { return _pointShader; }
FileLogger* getLogger() { return _logger; }
QPointF getViewportCenter() const
{ return QPointF(_glWidget->getDeviceWidth() / 2.0f, _glWidget->getDeviceHeight() / 2.0f); }
glm::vec2 getViewportDimensions() const { return glm::vec2(_glWidget->getDeviceWidth(), _glWidget->getDeviceHeight()); }
NodeToJurisdictionMap& getVoxelServerJurisdictions() { return _voxelServerJurisdictions; }
NodeToJurisdictionMap& getEntityServerJurisdictions() { return _entityServerJurisdictions; }

View file

@ -72,9 +72,9 @@ float Camera::getFarClip() const {
: std::numeric_limits<int16_t>::max() - 1;
}
void Camera::setMode(CameraMode m) {
_mode = m;
emit modeUpdated(m);
void Camera::setMode(CameraMode mode) {
_mode = mode;
emit modeUpdated(modeToString(mode));
}
@ -94,57 +94,45 @@ void Camera::setFarClip(float f) {
_farClip = f;
}
CameraScriptableObject::CameraScriptableObject(Camera* camera, ViewFrustum* viewFrustum) :
_camera(camera), _viewFrustum(viewFrustum)
{
connect(_camera, &Camera::modeUpdated, this, &CameraScriptableObject::onModeUpdated);
}
PickRay CameraScriptableObject::computePickRay(float x, float y) {
PickRay Camera::computePickRay(float x, float y) {
float screenWidth = Application::getInstance()->getGLWidget()->width();
float screenHeight = Application::getInstance()->getGLWidget()->height();
PickRay result;
if (OculusManager::isConnected()) {
result.origin = _camera->getPosition();
result.origin = getPosition();
Application::getInstance()->getApplicationOverlay().computeOculusPickRay(x / screenWidth, y / screenHeight, result.direction);
} else {
_viewFrustum->computePickRay(x / screenWidth, y / screenHeight, result.origin, result.direction);
Application::getInstance()->getViewFrustum()->computePickRay(x / screenWidth, y / screenHeight,
result.origin, result.direction);
}
return result;
}
QString CameraScriptableObject::getMode() const {
return modeToString(_camera->getMode());
}
void CameraScriptableObject::setMode(const QString& mode) {
CameraMode currentMode = _camera->getMode();
CameraMode targetMode = currentMode;
if (mode == "third person") {
targetMode = CAMERA_MODE_THIRD_PERSON;
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, false);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
} else if (mode == "first person") {
targetMode = CAMERA_MODE_FIRST_PERSON;
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, false);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, true);
} else if (mode == "mirror") {
targetMode = CAMERA_MODE_MIRROR;
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, true);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
} else if (mode == "independent") {
targetMode = CAMERA_MODE_INDEPENDENT;
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, false);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
void Camera::setModeString(const QString& mode) {
CameraMode targetMode = stringToMode(mode);
switch (targetMode) {
case CAMERA_MODE_THIRD_PERSON:
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, false);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
break;
case CAMERA_MODE_MIRROR:
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, true);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
break;
case CAMERA_MODE_INDEPENDENT:
Menu::getInstance()->setIsOptionChecked(MenuOption::FullscreenMirror, false);
Menu::getInstance()->setIsOptionChecked(MenuOption::FirstPerson, false);
break;
default:
break;
}
if (currentMode != targetMode) {
_camera->setMode(targetMode);
if (_mode != targetMode) {
setMode(targetMode);
}
}
void CameraScriptableObject::onModeUpdated(CameraMode m) {
emit modeUpdated(modeToString(m));
QString Camera::getModeString() const {
return modeToString(_mode);
}

View file

@ -32,6 +32,10 @@ static int cameraModeId = qRegisterMetaType<CameraMode>();
class Camera : public QObject {
Q_OBJECT
Q_PROPERTY(glm::vec3 position READ getPosition WRITE setPosition)
Q_PROPERTY(glm::quat orientation READ getOrientation WRITE setOrientation)
Q_PROPERTY(QString mode READ getModeString WRITE setModeString)
public:
Camera();
@ -39,7 +43,6 @@ public:
void update( float deltaTime );
void setPosition(const glm::vec3& p) { _position = p; }
void setRotation(const glm::quat& rotation) { _rotation = rotation; };
void setHmdPosition(const glm::vec3& hmdPosition) { _hmdPosition = hmdPosition; }
void setHmdRotation(const glm::quat& hmdRotation) { _hmdRotation = hmdRotation; };
@ -53,7 +56,6 @@ public:
void setEyeOffsetOrientation(const glm::quat& o) { _eyeOffsetOrientation = o; }
void setScale(const float s) { _scale = s; }
glm::vec3 getPosition() const { return _position + _hmdPosition; }
glm::quat getRotation() const { return _rotation * _hmdRotation; }
const glm::vec3& getHmdPosition() const { return _hmdPosition; }
const glm::quat& getHmdRotation() const { return _hmdRotation; }
@ -66,12 +68,21 @@ public:
const glm::vec3& getEyeOffsetPosition() const { return _eyeOffsetPosition; }
const glm::quat& getEyeOffsetOrientation() const { return _eyeOffsetOrientation; }
float getScale() const { return _scale; }
public slots:
QString getModeString() const;
void setModeString(const QString& mode);
signals:
void modeUpdated(CameraMode newMode);
glm::vec3 getPosition() const { return _position + _hmdPosition; }
void setPosition(const glm::vec3& position) { _position = position; }
private:
void setOrientation(const glm::quat& orientation) { setRotation(orientation); }
glm::quat getOrientation() const { return getRotation(); }
PickRay computePickRay(float x, float y);
signals:
void modeUpdated(const QString& newMode);
private:
CameraMode _mode;
glm::vec3 _position;
float _fieldOfView; // degrees
@ -88,32 +99,4 @@ private:
float _scale;
};
class CameraScriptableObject : public QObject {
Q_OBJECT
public:
CameraScriptableObject(Camera* camera, ViewFrustum* viewFrustum);
public slots:
QString getMode() const;
void setMode(const QString& mode);
void setPosition(const glm::vec3& value) { _camera->setPosition(value);}
glm::vec3 getPosition() const { return _camera->getPosition(); }
void setOrientation(const glm::quat& value) { _camera->setRotation(value); }
glm::quat getOrientation() const { return _camera->getRotation(); }
PickRay computePickRay(float x, float y);
signals:
void modeUpdated(const QString& newMode);
private slots:
void onModeUpdated(CameraMode m);
private:
Camera* _camera;
ViewFrustum* _viewFrustum;
};
#endif // hifi_Camera_h

View file

@ -1057,10 +1057,6 @@ float Avatar::getPelvisFloatingHeight() const {
return -_skeletonModel.getBindExtents().minimum.y;
}
float Avatar::getPelvisToHeadLength() const {
return glm::distance(_position, getHead()->getPosition());
}
void Avatar::setShowDisplayName(bool showDisplayName) {
if (!Menu::getInstance()->isOptionChecked(MenuOption::NamesAboveHeads)) {
_displayNameAlpha = 0.0f;

View file

@ -230,7 +230,6 @@ protected:
float getSkeletonHeight() const;
float getHeadHeight() const;
float getPelvisFloatingHeight() const;
float getPelvisToHeadLength() const;
glm::vec3 getDisplayNamePosition();
void renderDisplayName();

View file

@ -416,7 +416,7 @@ void MyAvatar::renderDebugBodyPoints() {
glPushMatrix();
glColor4f(0, 1, 0, .5f);
glTranslatef(position.x, position.y, position.z);
Application::getInstance()->getGeometryCache()->renderSphere(0.2, 10, 10);
Application::getInstance()->getGeometryCache()->renderSphere(0.2f, 10.0f, 10.0f);
glPopMatrix();
// Head Sphere
@ -424,7 +424,7 @@ void MyAvatar::renderDebugBodyPoints() {
glPushMatrix();
glColor4f(0, 1, 0, .5f);
glTranslatef(position.x, position.y, position.z);
Application::getInstance()->getGeometryCache()->renderSphere(0.15, 10, 10);
Application::getInstance()->getGeometryCache()->renderSphere(0.15f, 10.0f, 10.0f);
glPopMatrix();
}
@ -1004,10 +1004,6 @@ bool MyAvatar::isLookingAtLeftEye() {
return _isLookingAtLeftEye;
}
glm::vec3 MyAvatar::getUprightHeadPosition() const {
return _position + getWorldAlignedOrientation() * glm::vec3(0.0f, getPelvisToHeadLength(), 0.0f);
}
glm::vec3 MyAvatar::getDefaultEyePosition() const {
return _position + getWorldAlignedOrientation() * _skeletonModel.getDefaultEyeModelPosition();
}

View file

@ -66,7 +66,6 @@ public:
const glm::vec3& getMouseRayOrigin() const { return _mouseRayOrigin; }
const glm::vec3& getMouseRayDirection() const { return _mouseRayDirection; }
glm::vec3 getGravity() const { return _gravity; }
glm::vec3 getUprightHeadPosition() const;
glm::vec3 getDefaultEyePosition() const;
bool getShouldRenderLocally() const { return _shouldRender; }

View file

@ -420,7 +420,7 @@ void OculusManager::endFrameTiming() {
//Sets the camera FoV and aspect ratio
void OculusManager::configureCamera(Camera& camera, int screenWidth, int screenHeight) {
#ifdef HAVE_LIBOVR
camera.setAspectRatio(_renderTargetSize.w / _renderTargetSize.h);
camera.setAspectRatio((float)_renderTargetSize.w / _renderTargetSize.h);
camera.setFieldOfView(atan(_eyeFov[0].UpTan) * DEGREES_PER_RADIAN * 2.0f);
#endif
}
@ -511,12 +511,13 @@ void OculusManager::display(const glm::quat &bodyOrientation, const glm::vec3 &p
_camera->update(1.0f / Application::getInstance()->getFps());
Matrix4f proj = ovrMatrix4f_Projection(_eyeRenderDesc[eye].Fov, whichCamera.getNearClip(), whichCamera.getFarClip(), true);
proj.Transpose();
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glLoadMatrixf((GLfloat *)proj.M);
const ovrFovPort& port = _eyeFov[_activeEyeIndex];
float nearClip = whichCamera.getNearClip(), farClip = whichCamera.getFarClip();
glFrustum(-nearClip * port.LeftTan, nearClip * port.RightTan, -nearClip * port.DownTan,
nearClip * port.UpTan, nearClip, farClip);
glViewport(_eyeRenderViewport[eye].Pos.x, _eyeRenderViewport[eye].Pos.y,
_eyeRenderViewport[eye].Size.w, _eyeRenderViewport[eye].Size.h);

View file

@ -91,8 +91,10 @@ void TV3DManager::display(Camera& whichCamera) {
// left eye portal
int portalX = 0;
int portalY = 0;
int portalW = Application::getInstance()->getGLWidget()->getDeviceWidth() / 2;
int portalH = Application::getInstance()->getGLWidget()->getDeviceHeight();
QSize deviceSize = Application::getInstance()->getGLWidget()->getDeviceSize() *
Application::getInstance()->getRenderResolutionScale();
int portalW = deviceSize.width() / 2;
int portalH = deviceSize.height();
ApplicationOverlay& applicationOverlay = Application::getInstance()->getApplicationOverlay();
@ -135,7 +137,7 @@ void TV3DManager::display(Camera& whichCamera) {
glDisable(GL_SCISSOR_TEST);
// render right side view
portalX = Application::getInstance()->getGLWidget()->getDeviceWidth() / 2;
portalX = deviceSize.width() / 2;
glEnable(GL_SCISSOR_TEST);
// render left side view
glViewport(portalX, portalY, portalW, portalH);
@ -165,8 +167,7 @@ void TV3DManager::display(Camera& whichCamera) {
glDisable(GL_SCISSOR_TEST);
// reset the viewport to how we started
glViewport(0, 0, Application::getInstance()->getGLWidget()->getDeviceWidth(),
Application::getInstance()->getGLWidget()->getDeviceHeight());
glViewport(0, 0, deviceSize.width(), deviceSize.height());
Application::getInstance()->getGlowEffect()->render();
}

View file

@ -64,12 +64,6 @@ public:
/// clears the tree
virtual void clear();
//Q_INVOKABLE Model* getModel(const ModelEntityItem* modelEntityItem);
// renderers for various types of entities
void renderEntityTypeBox(EntityItem* entity, RenderArgs* args);
void renderEntityTypeModel(EntityItem* entity, RenderArgs* args);
static QThread* getMainThread();
/// if a renderable entity item needs a model, we will allocate it for them

View file

@ -51,8 +51,7 @@ void AmbientOcclusionEffect::init() {
_occlusionProgram->bind();
_occlusionProgram->setUniformValue("depthTexture", 0);
_occlusionProgram->setUniformValue("normalTexture", 1);
_occlusionProgram->setUniformValue("rotationTexture", 2);
_occlusionProgram->setUniformValue("rotationTexture", 1);
_occlusionProgram->setUniformValueArray("sampleKernel", sampleKernel, SAMPLE_KERNEL_SIZE);
_occlusionProgram->setUniformValue("radius", 0.1f);
_occlusionProgram->release();
@ -102,9 +101,6 @@ void AmbientOcclusionEffect::render() {
glBindTexture(GL_TEXTURE_2D, Application::getInstance()->getTextureCache()->getPrimaryDepthTextureID());
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, Application::getInstance()->getTextureCache()->getPrimaryNormalTextureID());
glActiveTexture(GL_TEXTURE2);
glBindTexture(GL_TEXTURE_2D, _rotationTextureID);
// render with the occlusion shader to the secondary/tertiary buffer
@ -142,9 +138,6 @@ void AmbientOcclusionEffect::render() {
glBindTexture(GL_TEXTURE_2D, 0);
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, 0);
glActiveTexture(GL_TEXTURE0);
// now render secondary to primary with 4x4 blur

View file

@ -78,3 +78,11 @@ void AudioDeviceScriptingInterface::setReverb(bool reverb) {
void AudioDeviceScriptingInterface::setReverbOptions(const AudioEffectOptions* options) {
Application::getInstance()->getAudio()->setReverbOptions(options);
}
void AudioDeviceScriptingInterface::toggleMute() {
Application::getInstance()->getAudio()->toggleMute();
}
bool AudioDeviceScriptingInterface::getMuted() {
return Application::getInstance()->getAudio()->getMuted();
}

View file

@ -41,6 +41,12 @@ public slots:
void setInputVolume(float volume);
void setReverb(bool reverb);
void setReverbOptions(const AudioEffectOptions* options);
bool getMuted();
void toggleMute();
signals:
void muteToggled();
};
#endif // hifi_AudioDeviceScriptingInterface_h

View file

@ -129,9 +129,8 @@ void JoystickScriptingInterface::update() {
: HFActionEvent::endType();
// global action events fire in the center of the screen
QPointF centerPoint = Application::getInstance()->getViewportCenter();
HFActionEvent actionEvent(actionType, centerPoint);
HFActionEvent actionEvent(actionType,
Application::getInstance()->getViewFrustum()->computePickRay(0.5f, 0.5f));
qApp->sendEvent(qApp, &actionEvent);
}

View file

@ -183,7 +183,7 @@ void ApplicationOverlay::computeOculusPickRay(float x, float y, glm::vec3& direc
float dist = sqrt(x * x + y * y);
float z = -sqrt(1.0f - dist * dist);
glm::vec3 relativePosition = myAvatar->getHead()->getEyePosition() +
glm::vec3 relativePosition = myAvatar->getDefaultEyePosition() +
glm::normalize(myAvatar->getOrientation() * glm::vec3(x, y, z));
//Rotate the UI pick ray by the avatar orientation
@ -380,7 +380,7 @@ void ApplicationOverlay::displayOverlayTextureOculus(Camera& whichCamera) {
glPushMatrix();
const glm::quat& orientation = myAvatar->getOrientation();
const glm::vec3& position = myAvatar->getHead()->getEyePosition();
const glm::vec3& position = myAvatar->getDefaultEyePosition();
glm::mat4 rotation = glm::toMat4(orientation);
@ -414,7 +414,7 @@ void ApplicationOverlay::displayOverlayTextureOculus(Camera& whichCamera) {
renderTexturedHemisphere();
renderPointersOculus(myAvatar->getHead()->getEyePosition());
renderPointersOculus(myAvatar->getDefaultEyePosition());
glDepthMask(GL_TRUE);
glBindTexture(GL_TEXTURE_2D, 0);
@ -1220,7 +1220,7 @@ void ApplicationOverlay::renderTexturedHemisphere() {
Application* application = Application::getInstance();
MyAvatar* myAvatar = application->getAvatar();
const glm::quat& orientation = myAvatar->getOrientation();
const glm::vec3& position = myAvatar->getHead()->getEyePosition();
const glm::vec3& position = myAvatar->getDefaultEyePosition();
glm::mat4 rotation = glm::toMat4(orientation);

View file

@ -14,6 +14,7 @@
#include <QtCore/QJsonDocument>
#include "Assignment.h"
#include "HifiSockAddr.h"
#include "NodeList.h"
#include "PacketHeaders.h"
#include "UserActivityLogger.h"
@ -144,7 +145,10 @@ void DomainHandler::setIceServerHostnameAndID(const QString& iceServerHostname,
hardReset();
_iceDomainID = id;
_iceServerSockAddr = HifiSockAddr(iceServerHostname, ICE_SERVER_DEFAULT_PORT);
HifiSockAddr* replaceableSockAddr = &_iceServerSockAddr;
replaceableSockAddr->~HifiSockAddr();
replaceableSockAddr = new (replaceableSockAddr) HifiSockAddr(iceServerHostname, ICE_SERVER_DEFAULT_PORT);
// refresh our ICE client UUID to something new
_iceClientID = QUuid::createUuid();

View file

@ -31,9 +31,17 @@ HifiSockAddr::HifiSockAddr(const QHostAddress& address, quint16 port) :
}
HifiSockAddr::HifiSockAddr(const HifiSockAddr& otherSockAddr) {
_address = otherSockAddr._address;
_port = otherSockAddr._port;
HifiSockAddr::HifiSockAddr(const HifiSockAddr& otherSockAddr) :
_address(otherSockAddr._address),
_port(otherSockAddr._port)
{
}
HifiSockAddr& HifiSockAddr::operator=(const HifiSockAddr& rhsSockAddr) {
HifiSockAddr temp(rhsSockAddr);
swap(temp);
return *this;
}
HifiSockAddr::HifiSockAddr(const QString& hostname, quint16 hostOrderPort, bool shouldBlockForLookup) :
@ -44,12 +52,12 @@ HifiSockAddr::HifiSockAddr(const QString& hostname, quint16 hostOrderPort, bool
if (_address.protocol() != QAbstractSocket::IPv4Protocol) {
// lookup the IP by the hostname
if (shouldBlockForLookup) {
qDebug() << "Asynchronously looking up IP address for hostname" << hostname;
qDebug() << "Synchronously looking up IP address for hostname" << hostname;
QHostInfo result = QHostInfo::fromName(hostname);
handleLookupResult(result);
} else {
int lookupID = QHostInfo::lookupHost(hostname, this, SLOT(handleLookupResult(QHostInfo)));
qDebug() << "Synchronously looking up IP address for hostname" << hostname << "- lookup ID is" << lookupID;
qDebug() << "Asynchronously looking up IP address for hostname" << hostname << "- lookup ID is" << lookupID;
}
}
}
@ -64,13 +72,6 @@ HifiSockAddr::HifiSockAddr(const sockaddr* sockaddr) {
}
}
HifiSockAddr& HifiSockAddr::operator=(const HifiSockAddr& rhsSockAddr) {
_address = rhsSockAddr._address;
_port = rhsSockAddr._port;
return *this;
}
void HifiSockAddr::swap(HifiSockAddr& otherSockAddr) {
using std::swap;

View file

@ -583,6 +583,13 @@ bool ViewFrustum::isVerySimilar(const ViewFrustum& compareTo, bool debug) const
return result;
}
PickRay ViewFrustum::computePickRay(float x, float y) {
glm::vec3 pickRayOrigin;
glm::vec3 pickRayDirection;
computePickRay(x, y, pickRayOrigin, pickRayDirection);
return PickRay(pickRayOrigin, pickRayDirection);
}
void ViewFrustum::computePickRay(float x, float y, glm::vec3& origin, glm::vec3& direction) const {
origin = _nearTopLeft + x*(_nearTopRight - _nearTopLeft) + y*(_nearBottomLeft - _nearTopLeft);
direction = glm::normalize(origin - (_position + _orientation * _eyeOffsetPosition));

View file

@ -17,6 +17,8 @@
#include <glm/glm.hpp>
#include <glm/gtc/quaternion.hpp>
#include <RegisteredMetaTypes.h>
#include "AABox.h"
#include "AACube.h"
#include "Plane.h"
@ -105,6 +107,7 @@ public:
bool isVerySimilar(const ViewFrustum& compareTo, bool debug = false) const;
bool isVerySimilar(const ViewFrustum* compareTo, bool debug = false) const { return isVerySimilar(*compareTo, debug); }
PickRay computePickRay(float x, float y);
void computePickRay(float x, float y, glm::vec3& origin, glm::vec3& direction) const;
void computeOffAxisFrustum(float& left, float& right, float& bottom, float& top, float& nearValue, float& farValue,

View file

@ -11,9 +11,9 @@
#include "HFActionEvent.h"
HFActionEvent::HFActionEvent(QEvent::Type type, const QPointF& localPosition) :
HFActionEvent::HFActionEvent(QEvent::Type type, const PickRay& actionRay) :
HFMetaEvent(type),
localPosition(localPosition)
actionRay(actionRay)
{
}
@ -30,8 +30,7 @@ QEvent::Type HFActionEvent::endType() {
QScriptValue HFActionEvent::toScriptValue(QScriptEngine* engine, const HFActionEvent& event) {
QScriptValue obj = engine->newObject();
obj.setProperty("x", event.localPosition.x());
obj.setProperty("y", event.localPosition.y());
obj.setProperty("actionRay", pickRayToScriptValue(engine, event.actionRay));
return obj;
}

View file

@ -12,14 +12,17 @@
#ifndef hifi_HFActionEvent_h
#define hifi_HFActionEvent_h
#include "HFMetaEvent.h"
#include <qscriptengine.h>
#include <RegisteredMetaTypes.h>
#include "HFMetaEvent.h"
class HFActionEvent : public HFMetaEvent {
public:
HFActionEvent() {};
HFActionEvent(QEvent::Type type, const QPointF& localPosition);
HFActionEvent(QEvent::Type type, const PickRay& actionRay);
static QEvent::Type startType();
static QEvent::Type endType();
@ -27,7 +30,7 @@ public:
static QScriptValue toScriptValue(QScriptEngine* engine, const HFActionEvent& event);
static void fromScriptValue(const QScriptValue& object, HFActionEvent& event);
QPointF localPosition;
PickRay actionRay;
};
Q_DECLARE_METATYPE(HFActionEvent)

View file

@ -53,7 +53,8 @@ void qURLFromScriptValue(const QScriptValue& object, QUrl& url);
class PickRay {
public:
PickRay() : origin(0.0f), direction(0.0f) { }
PickRay() : origin(0.0f), direction(0.0f) { }
PickRay(const glm::vec3& origin, const glm::vec3 direction) : origin(origin), direction(direction) {}
glm::vec3 origin;
glm::vec3 direction;
};

View file

@ -46,6 +46,26 @@ quint64 usecTimestampNow() {
TIME_REFERENCE = QDateTime::currentMSecsSinceEpoch() * 1000; // ms to usec
timestampTimer.start();
usecTimestampNowIsInitialized = true;
} else {
// We've seen the QElapsedTimer begin to introduce dramatic errors if it's been
// continuously running for a long time. So we will periodically reset it.
const quint64 SECS_TO_NSECS = 1000000000;
const quint64 RESET_AFTER_ELAPSED_SECS = 60 * 60; // 1 hour: 60 minutes * 60 seconds
const quint64 RESET_AFTER_ELAPSED_NSECS = RESET_AFTER_ELAPSED_SECS * SECS_TO_NSECS;
const quint64 nsecsElapsed = timestampTimer.nsecsElapsed();
if (nsecsElapsed > RESET_AFTER_ELAPSED_NSECS) {
quint64 msecsElapsed = timestampTimer.restart();
quint64 usecsElapsed = nsecsElapsed / 1000; // nsec to usec
TIME_REFERENCE += usecsElapsed;
const bool wantDebug = false;
if (wantDebug) {
qDebug() << "usecTimestampNow() - resetting QElapsedTimer. ";
qDebug() << " RESET_AFTER_ELAPSED_NSECS:" << RESET_AFTER_ELAPSED_NSECS;
qDebug() << " nsecsElapsed:" << nsecsElapsed;
qDebug() << " msecsElapsed:" << msecsElapsed;
qDebug() << " usecsElapsed:" << usecsElapsed;
}
}
}
// usec nsec to usec usec