Merge branch 'master' into hazeZone

This commit is contained in:
Nissim 2017-10-19 13:39:18 -07:00
commit 61fc45c6bf
83 changed files with 835 additions and 513 deletions

View file

@ -118,6 +118,7 @@ macro(AUTOSCRIBE_SHADER_LIB)
foreach(SHADER_FILE ${SHADER_SOURCE_FILES}) foreach(SHADER_FILE ${SHADER_SOURCE_FILES})
AUTOSCRIBE_SHADER(${SHADER_FILE} ${SHADER_INCLUDE_FILES}) AUTOSCRIBE_SHADER(${SHADER_FILE} ${SHADER_INCLUDE_FILES})
file(TO_CMAKE_PATH "${AUTOSCRIBE_SHADER_RETURN}" AUTOSCRIBE_GENERATED_FILE) file(TO_CMAKE_PATH "${AUTOSCRIBE_SHADER_RETURN}" AUTOSCRIBE_GENERATED_FILE)
set_property(SOURCE ${AUTOSCRIBE_GENERATED_FILE} PROPERTY SKIP_AUTOMOC ON)
list(APPEND AUTOSCRIBE_SHADER_SRC ${AUTOSCRIBE_GENERATED_FILE}) list(APPEND AUTOSCRIBE_SHADER_SRC ${AUTOSCRIBE_GENERATED_FILE})
endforeach() endforeach()
#message(${TARGET_NAME} ${AUTOSCRIBE_SHADER_SRC}) #message(${TARGET_NAME} ${AUTOSCRIBE_SHADER_SRC})

View file

@ -0,0 +1,20 @@
function(GENERATE_QRC)
set(oneValueArgs OUTPUT PREFIX PATH)
set(multiValueArgs GLOBS)
cmake_parse_arguments(GENERATE_QRC "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN} )
if ("${GENERATE_QRC_PREFIX}" STREQUAL "")
set(QRC_PREFIX_PATH /)
else()
set(QRC_PREFIX_PATH ${GENERATE_QRC_PREFIX})
endif()
foreach(GLOB ${GENERATE_QRC_GLOBS})
file(GLOB_RECURSE FOUND_FILES RELATIVE ${GENERATE_QRC_PATH} ${GLOB})
foreach(FILENAME ${FOUND_FILES})
set(QRC_CONTENTS "${QRC_CONTENTS}<file alias=\"${FILENAME}\">${GENERATE_QRC_PATH}/${FILENAME}</file>\n")
endforeach()
endforeach()
configure_file("${HF_CMAKE_DIR}/templates/resources.qrc.in" ${GENERATE_QRC_OUTPUT})
endfunction()

View file

@ -7,10 +7,12 @@
# #
function(set_from_env _RESULT_NAME _ENV_VAR_NAME _DEFAULT_VALUE) function(set_from_env _RESULT_NAME _ENV_VAR_NAME _DEFAULT_VALUE)
if ("$ENV{${_ENV_VAR_NAME}}" STREQUAL "") if (NOT DEFINED ${_RESULT_NAME})
set (${_RESULT_NAME} ${_DEFAULT_VALUE} PARENT_SCOPE) if ("$ENV{${_ENV_VAR_NAME}}" STREQUAL "")
else() set (${_RESULT_NAME} ${_DEFAULT_VALUE} PARENT_SCOPE)
set (${_RESULT_NAME} $ENV{${_ENV_VAR_NAME}} PARENT_SCOPE) else()
set (${_RESULT_NAME} $ENV{${_ENV_VAR_NAME}} PARENT_SCOPE)
endif()
endif() endif()
endfunction() endfunction()

View file

@ -0,0 +1,5 @@
<!DOCTYPE RCC><RCC version="1.0">
<qresource prefix="@QRC_PREFIX_PATH@">
@QRC_CONTENTS@
</qresource>
</RCC>

View file

@ -1,6 +1,20 @@
set(TARGET_NAME interface) set(TARGET_NAME interface)
project(${TARGET_NAME}) project(${TARGET_NAME})
file(GLOB_RECURSE QML_SRC resources/qml/*.qml resources/qml/*.js)
add_custom_target(qml SOURCES ${QML_SRC})
GroupSources("resources/qml")
function(JOIN VALUES GLUE OUTPUT)
string (REGEX REPLACE "([^\\]|^);" "\\1${GLUE}" _TMP_STR "${VALUES}")
string (REGEX REPLACE "[\\](.)" "\\1" _TMP_STR "${_TMP_STR}") #fixes escaping
set (${OUTPUT} "${_TMP_STR}" PARENT_SCOPE)
endfunction()
set(INTERFACE_QML_QRC ${CMAKE_CURRENT_BINARY_DIR}/qml.qrc)
generate_qrc(OUTPUT ${INTERFACE_QML_QRC} PATH ${CMAKE_CURRENT_SOURCE_DIR}/resources GLOBS *.qml *.qss *.js *.html *.ttf *.gif *.svg *.png *.jpg)
# set a default root dir for each of our optional externals if it was not passed # set a default root dir for each of our optional externals if it was not passed
set(OPTIONAL_EXTERNALS "LeapMotion") set(OPTIONAL_EXTERNALS "LeapMotion")
@ -66,9 +80,7 @@ qt5_wrap_ui(QT_UI_HEADERS "${QT_UI_FILES}")
# add them to the interface source files # add them to the interface source files
set(INTERFACE_SRCS ${INTERFACE_SRCS} "${QT_UI_HEADERS}" "${QT_RESOURCES}") set(INTERFACE_SRCS ${INTERFACE_SRCS} "${QT_UI_HEADERS}" "${QT_RESOURCES}")
file(GLOB_RECURSE QML_SRC resources/qml/*.qml resources/qml/*.js) list(APPEND INTERFACE_SRCS ${INTERFACE_QML_QRC})
add_custom_target(qml SOURCES ${QML_SRC})
GroupSources("resources/qml")
if (UNIX) if (UNIX)
install( install(
@ -131,10 +143,10 @@ if (APPLE)
# append the discovered resources to our list of interface sources # append the discovered resources to our list of interface sources
list(APPEND INTERFACE_SRCS ${DISCOVERED_RESOURCES}) list(APPEND INTERFACE_SRCS ${DISCOVERED_RESOURCES})
list(APPEND INTERFACE_SRCS ${CMAKE_CURRENT_SOURCE_DIR}/icon/${INTERFACE_ICON_FILENAME})
set(INTERFACE_SRCS ${INTERFACE_SRCS} "${CMAKE_CURRENT_SOURCE_DIR}/icon/${INTERFACE_ICON_FILENAME}")
endif() endif()
# create the executable, make it a bundle on OS X # create the executable, make it a bundle on OS X
if (APPLE) if (APPLE)
add_executable(${TARGET_NAME} MACOSX_BUNDLE ${INTERFACE_SRCS} ${QM}) add_executable(${TARGET_NAME} MACOSX_BUNDLE ${INTERFACE_SRCS} ${QM})

Binary file not shown.

Before

Width:  |  Height:  |  Size: 312 KiB

After

Width:  |  Height:  |  Size: 604 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 232 KiB

After

Width:  |  Height:  |  Size: 503 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 307 KiB

After

Width:  |  Height:  |  Size: 585 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 268 KiB

After

Width:  |  Height:  |  Size: 547 KiB

View file

@ -18,7 +18,7 @@
function shouldRaiseKeyboard() { function shouldRaiseKeyboard() {
var nodeName = document.activeElement.nodeName; var nodeName = document.activeElement.nodeName;
var nodeType = document.activeElement.type; var nodeType = document.activeElement.type;
if (nodeName === "INPUT" && ["email", "number", "password", "tel", "text", "url"].indexOf(nodeType) !== -1 if (nodeName === "INPUT" && ["email", "number", "password", "tel", "text", "url", "search"].indexOf(nodeType) !== -1
|| document.activeElement.nodeName === "TEXTAREA") { || document.activeElement.nodeName === "TEXTAREA") {
return true; return true;
} else { } else {

View file

@ -239,6 +239,25 @@ Rectangle {
} }
} }
} }
}
HifiCommerceCommon.FirstUseTutorial {
id: firstUseTutorial;
z: 999;
visible: root.activeView === "firstUseTutorial";
anchors.fill: parent;
Connections {
onSendSignalToParent: {
switch (message.method) {
case 'tutorial_skipClicked':
case 'tutorial_finished':
Settings.setValue("isFirstUseOfPurchases", false);
root.activeView = "checkoutSuccess";
break;
}
}
}
} }
// //
@ -611,6 +630,28 @@ Rectangle {
lightboxPopup.visible = true; lightboxPopup.visible = true;
} }
} }
RalewaySemiBold {
id: explainRezText;
//visible: !root.isWearable;
text: '<font color="' + hifi.colors.redAccent + '"><a href="#">What does "Rez" mean?</a></font>'
// Text size
size: 16;
// Anchors
anchors.top: noPermissionText.visible ? noPermissionText.bottom : rezNowButton.bottom;
anchors.topMargin: 6;
height: paintedHeight;
anchors.left: parent.left;
anchors.right: parent.right;
// Style
color: hifi.colors.redAccent;
wrapMode: Text.WordWrap;
// Alignment
horizontalAlignment: Text.AlignHCenter;
verticalAlignment: Text.AlignVCenter;
onLinkActivated: {
root.activeView = "firstUseTutorial";
}
}
RalewaySemiBold { RalewaySemiBold {
id: myPurchasesLink; id: myPurchasesLink;
@ -618,7 +659,7 @@ Rectangle {
// Text size // Text size
size: 20; size: 20;
// Anchors // Anchors
anchors.top: noPermissionText.visible ? noPermissionText.bottom : rezNowButton.bottom; anchors.top: explainRezText.visible ? explainRezText.bottom : (noPermissionText.visible ? noPermissionText.bottom : rezNowButton.bottom);
anchors.topMargin: 40; anchors.topMargin: 40;
height: paintedHeight; height: paintedHeight;
anchors.left: parent.left; anchors.left: parent.left;

View file

@ -25,7 +25,13 @@ Rectangle {
HifiConstants { id: hifi; } HifiConstants { id: hifi; }
id: root; id: root;
property int activeView: 1; property int activeView: 1;
onVisibleChanged: {
if (visible) {
root.activeView = 1;
}
}
Image { Image {
anchors.fill: parent; anchors.fill: parent;

View file

@ -200,12 +200,6 @@ Rectangle {
// Style // Style
color: hifi.colors.lightGray; color: hifi.colors.lightGray;
} }
FontLoader { id: ralewayRegular; source: "../../../../fonts/Raleway-Regular.ttf"; }
TextMetrics {
id: textMetrics;
font.family: ralewayRegular.name
text: root.itemOwner;
}
RalewayRegular { RalewayRegular {
id: ownedBy; id: ownedBy;
text: root.itemOwner; text: root.itemOwner;
@ -215,8 +209,7 @@ Rectangle {
anchors.top: ownedByHeader.bottom; anchors.top: ownedByHeader.bottom;
anchors.topMargin: 8; anchors.topMargin: 8;
anchors.left: ownedByHeader.left; anchors.left: ownedByHeader.left;
height: textMetrics.height; height: paintedHeight;
width: root.isMyCert ? textMetrics.width + 25 : ownedByHeader.width;
// Style // Style
color: hifi.colors.darkGray; color: hifi.colors.darkGray;
elide: Text.ElideRight; elide: Text.ElideRight;
@ -231,7 +224,7 @@ Rectangle {
anchors.topMargin: 4; anchors.topMargin: 4;
anchors.bottom: ownedBy.bottom; anchors.bottom: ownedBy.bottom;
anchors.left: ownedBy.right; anchors.left: ownedBy.right;
anchors.leftMargin: 4; anchors.leftMargin: 6;
anchors.right: ownedByHeader.right; anchors.right: ownedByHeader.right;
// Style // Style
color: hifi.colors.lightGray; color: hifi.colors.lightGray;

View file

@ -241,7 +241,7 @@ Rectangle {
} }
} }
FirstUseTutorial { HifiCommerceCommon.FirstUseTutorial {
id: firstUseTutorial; id: firstUseTutorial;
z: 999; z: 999;
visible: root.activeView === "firstUseTutorial"; visible: root.activeView === "firstUseTutorial";

View file

@ -25,6 +25,7 @@ Item {
id: root; id: root;
property string keyFilePath; property string keyFilePath;
property bool showDebugButtons: true;
Hifi.QmlCommerce { Hifi.QmlCommerce {
id: commerce; id: commerce;
@ -56,6 +57,7 @@ Item {
} }
HifiControlsUit.Button { HifiControlsUit.Button {
id: clearCachedPassphraseButton; id: clearCachedPassphraseButton;
visible: root.showDebugButtons;
color: hifi.buttons.black; color: hifi.buttons.black;
colorScheme: hifi.colorSchemes.dark; colorScheme: hifi.colorSchemes.dark;
anchors.top: parent.top; anchors.top: parent.top;
@ -71,6 +73,7 @@ Item {
} }
HifiControlsUit.Button { HifiControlsUit.Button {
id: resetButton; id: resetButton;
visible: root.showDebugButtons;
color: hifi.buttons.red; color: hifi.buttons.red;
colorScheme: hifi.colorSchemes.dark; colorScheme: hifi.colorSchemes.dark;
anchors.top: clearCachedPassphraseButton.top; anchors.top: clearCachedPassphraseButton.top;
@ -90,17 +93,22 @@ Item {
ListElement { ListElement {
isExpanded: false; isExpanded: false;
question: "What are private keys?" question: "What are private keys?"
answer: qsTr("A private key is a secret piece of text that is used to decrypt code.<br><br>In High Fidelity, <b>your private keys are used to decrypt the contents of your Wallet and Purchases.</b>"); answer: qsTr("A private key is a secret piece of text that is used to prove ownership, unlock confidential information, and sign transactions.<br><br>In High Fidelity, <b>your private keys are used to securely access the contents of your Wallet and Purchases.</b>");
} }
ListElement { ListElement {
isExpanded: false; isExpanded: false;
question: "Where are my private keys stored?" question: "Where are my private keys stored?"
answer: qsTr('Your private keys are <b>only stored on your hard drive</b> in High Fidelity Interface\'s AppData directory.<br><br><b><font color="#0093C5"><a href="#privateKeyPath">Tap here to open the file path of your hifikey in your file explorer.</a></font></b><br><br> You may backup this file by copying it to a USB flash drive, or to a service like Dropbox or Google Drive. Restore your backup by replacing the file in Interface\'s AppData directory with your backed-up copy.'); answer: qsTr('By default, your private keys are <b>only stored on your hard drive</b> in High Fidelity Interface\'s AppData directory.<br><br><b><font color="#0093C5"><a href="#privateKeyPath">Tap here to open the folder where your HifiKeys are stored on your main display.</a></font></b>');
}
ListElement {
isExpanded: false;
question: "How can I backup my private keys?"
answer: qsTr('You may backup the file containing your private keys by copying it to a USB flash drive, or to a service like Dropbox or Google Drive.<br><br>Restore your backup by replacing the file in Interface\'s AppData directory with your backed-up copy.<br><br><b><font color="#0093C5"><a href="#privateKeyPath">Tap here to open the folder where your HifiKeys are stored on your main display.</a></font></b>');
} }
ListElement { ListElement {
isExpanded: false; isExpanded: false;
question: "What happens if I lose my passphrase?" question: "What happens if I lose my passphrase?"
answer: qsTr("If you lose your passphrase, you will no longer have access to the contents of your Wallet or My Purchases.<br><br><b>Nobody can help you recover your passphrase, including High Fidelity.</b> Please write it down and store it securely."); answer: qsTr("Your passphrase is used to encrypt your private keys. If you lose your passphrase, you will no longer be able to decrypt your private key file. You will also no longer have access to the contents of your Wallet or My Purchases.<br><br><b>Nobody can help you recover your passphrase, including High Fidelity.</b> Please write it down and store it securely.");
} }
ListElement { ListElement {
isExpanded: false; isExpanded: false;

View file

@ -25,7 +25,7 @@ Item {
HifiConstants { id: hifi; } HifiConstants { id: hifi; }
id: root; id: root;
z: 998; z: 997;
property bool keyboardRaised: false; property bool keyboardRaised: false;
property string titleBarIcon: ""; property string titleBarIcon: "";
property string titleBarText: ""; property string titleBarText: "";
@ -350,7 +350,7 @@ Item {
Item { Item {
id: keyboardContainer; id: keyboardContainer;
z: 999; z: 998;
visible: keyboard.raised; visible: keyboard.raised;
property bool punctuationMode: false; property bool punctuationMode: false;
anchors { anchors {
@ -361,11 +361,13 @@ Item {
Image { Image {
id: lowerKeyboardButton; id: lowerKeyboardButton;
z: 999;
source: "images/lowerKeyboard.png"; source: "images/lowerKeyboard.png";
anchors.horizontalCenter: parent.horizontalCenter; anchors.right: keyboard.right;
anchors.bottom: keyboard.top; anchors.top: keyboard.showMirrorText ? keyboard.top : undefined;
height: 30; anchors.bottom: keyboard.showMirrorText ? undefined : keyboard.bottom;
width: 120; height: 50;
width: 60;
MouseArea { MouseArea {
anchors.fill: parent; anchors.fill: parent;

View file

@ -290,7 +290,17 @@ Item {
id: removeHmdContainer; id: removeHmdContainer;
z: 998; z: 998;
visible: false; visible: false;
color: hifi.colors.blueHighlight;
gradient: Gradient {
GradientStop {
position: 0.2;
color: hifi.colors.baseGrayHighlight;
}
GradientStop {
position: 1.0;
color: hifi.colors.baseGrayShadow;
}
}
anchors.fill: backupInstructionsButton; anchors.fill: backupInstructionsButton;
radius: 5; radius: 5;
MouseArea { MouseArea {

View file

@ -165,7 +165,7 @@ Rectangle {
WalletSetup { WalletSetup {
id: walletSetup; id: walletSetup;
visible: root.activeView === "walletSetup"; visible: root.activeView === "walletSetup";
z: 998; z: 997;
anchors.fill: parent; anchors.fill: parent;
Connections { Connections {
@ -192,7 +192,7 @@ Rectangle {
PassphraseChange { PassphraseChange {
id: passphraseChange; id: passphraseChange;
visible: root.activeView === "passphraseChange"; visible: root.activeView === "passphraseChange";
z: 998; z: 997;
anchors.top: titleBarContainer.bottom; anchors.top: titleBarContainer.bottom;
anchors.left: parent.left; anchors.left: parent.left;
anchors.right: parent.right; anchors.right: parent.right;
@ -217,7 +217,7 @@ Rectangle {
SecurityImageChange { SecurityImageChange {
id: securityImageChange; id: securityImageChange;
visible: root.activeView === "securityImageChange"; visible: root.activeView === "securityImageChange";
z: 998; z: 997;
anchors.top: titleBarContainer.bottom; anchors.top: titleBarContainer.bottom;
anchors.left: parent.left; anchors.left: parent.left;
anchors.right: parent.right; anchors.right: parent.right;
@ -653,7 +653,7 @@ Rectangle {
Item { Item {
id: keyboardContainer; id: keyboardContainer;
z: 999; z: 998;
visible: keyboard.raised; visible: keyboard.raised;
property bool punctuationMode: false; property bool punctuationMode: false;
anchors { anchors {
@ -664,11 +664,13 @@ Rectangle {
Image { Image {
id: lowerKeyboardButton; id: lowerKeyboardButton;
z: 999;
source: "images/lowerKeyboard.png"; source: "images/lowerKeyboard.png";
anchors.horizontalCenter: parent.horizontalCenter; anchors.right: keyboard.right;
anchors.bottom: keyboard.top; anchors.top: keyboard.showMirrorText ? keyboard.top : undefined;
height: 30; anchors.bottom: keyboard.showMirrorText ? undefined : keyboard.bottom;
width: 120; height: 50;
width: 60;
MouseArea { MouseArea {
anchors.fill: parent; anchors.fill: parent;

View file

@ -164,7 +164,7 @@ Item {
anchors.top: parent.top; anchors.top: parent.top;
anchors.topMargin: 26; anchors.topMargin: 26;
anchors.left: parent.left; anchors.left: parent.left;
anchors.leftMargin: 30; anchors.leftMargin: 20;
anchors.right: parent.right; anchors.right: parent.right;
anchors.rightMargin: 30; anchors.rightMargin: 30;
height: 30; height: 30;

View file

@ -679,7 +679,7 @@ Item {
anchors.right: parent.right; anchors.right: parent.right;
anchors.rightMargin: 30; anchors.rightMargin: 30;
height: 40; height: 40;
text: "Open Instructions for Later"; text: "Open Backup Instructions for Later";
onClicked: { onClicked: {
instructions01Container.visible = false; instructions01Container.visible = false;
instructions02Container.visible = true; instructions02Container.visible = true;

Binary file not shown.

Before

Width:  |  Height:  |  Size: 721 B

After

Width:  |  Height:  |  Size: 1.2 KiB

View file

@ -19,6 +19,7 @@ Window {
shown: true shown: true
width: content.width width: content.width
height: content.height height: content.height
disableFade: true
// Disable this window from being able to call 'desktop.raise() and desktop.showDesktop' // Disable this window from being able to call 'desktop.raise() and desktop.showDesktop'
activator: Item {} activator: Item {}
property bool horizontal: true property bool horizontal: true

View file

@ -26,6 +26,7 @@ FocusScope {
property var completionCallback; property var completionCallback;
// The target property to animate, usually scale or opacity // The target property to animate, usually scale or opacity
property alias fadeTargetProperty: root.opacity property alias fadeTargetProperty: root.opacity
property bool disableFade: false
// always start the property at 0 to enable fade in on creation // always start the property at 0 to enable fade in on creation
fadeTargetProperty: 0 fadeTargetProperty: 0
// DO NOT set visible to false or when derived types override it it // DO NOT set visible to false or when derived types override it it
@ -35,6 +36,9 @@ FocusScope {
// Some dialogs should be destroyed when they become // Some dialogs should be destroyed when they become
// invisible, so handle that // invisible, so handle that
onVisibleChanged: { onVisibleChanged: {
if (disableFade) {
return;
}
// If someone directly set the visibility to false // If someone directly set the visibility to false
// toggle it back on and use the targetVisible flag to transition // toggle it back on and use the targetVisible flag to transition
// via fading. // via fading.
@ -62,7 +66,9 @@ FocusScope {
} }
onFadeTargetPropertyChanged: { onFadeTargetPropertyChanged: {
visible = (fadeTargetProperty != 0.0); if (!disableFade) {
visible = (fadeTargetProperty != 0.0);
}
} }
function fadeIn(callback) { function fadeIn(callback) {

View file

@ -2255,7 +2255,7 @@ void Application::initializeUi() {
offscreenUi->setBaseUrl(QUrl::fromLocalFile(PathUtils::resourcesPath() + "/qml/")); offscreenUi->setBaseUrl(QUrl::fromLocalFile(PathUtils::resourcesPath() + "/qml/"));
// OffscreenUi is a subclass of OffscreenQmlSurface specifically designed to // OffscreenUi is a subclass of OffscreenQmlSurface specifically designed to
// support the window management and scripting proxies for VR use // support the window management and scripting proxies for VR use
offscreenUi->createDesktop(QString("hifi/Desktop.qml")); offscreenUi->createDesktop(QString("qrc:///qml/hifi/Desktop.qml"));
// FIXME either expose so that dialogs can set this themselves or // FIXME either expose so that dialogs can set this themselves or
// do better detection in the offscreen UI of what has focus // do better detection in the offscreen UI of what has focus

View file

@ -16,6 +16,8 @@
#include <glm/glm.hpp> #include <glm/glm.hpp>
#include <QUuid>
#include <SettingHandle.h> #include <SettingHandle.h>
#include <Rig.h> #include <Rig.h>
#include <Sound.h> #include <Sound.h>
@ -106,6 +108,8 @@ class MyAvatar : public Avatar {
* "scripts/system/controllers/toggleAdvancedMovementForHandControllers.js". * "scripts/system/controllers/toggleAdvancedMovementForHandControllers.js".
* @property userHeight {number} The height of the user in sensor space. (meters). * @property userHeight {number} The height of the user in sensor space. (meters).
* @property userEyeHeight {number} Estimated height of the users eyes in sensor space. (meters) * @property userEyeHeight {number} Estimated height of the users eyes in sensor space. (meters)
* @property SELF_ID {string} READ-ONLY. UUID representing "my avatar". Only use for local-only entities and overlays in situations where MyAvatar.sessionUUID is not available (e.g., if not connected to a domain).
* Note: Likely to be deprecated.
*/ */
// FIXME: `glm::vec3 position` is not accessible from QML, so this exposes position in a QML-native type // FIXME: `glm::vec3 position` is not accessible from QML, so this exposes position in a QML-native type
@ -152,6 +156,8 @@ class MyAvatar : public Avatar {
Q_PROPERTY(float userHeight READ getUserHeight WRITE setUserHeight) Q_PROPERTY(float userHeight READ getUserHeight WRITE setUserHeight)
Q_PROPERTY(float userEyeHeight READ getUserEyeHeight) Q_PROPERTY(float userEyeHeight READ getUserEyeHeight)
Q_PROPERTY(QUuid SELF_ID READ getSelfID CONSTANT)
const QString DOMINANT_LEFT_HAND = "left"; const QString DOMINANT_LEFT_HAND = "left";
const QString DOMINANT_RIGHT_HAND = "right"; const QString DOMINANT_RIGHT_HAND = "right";
@ -546,6 +552,8 @@ public:
virtual SpatialParentTree* getParentTree() const override; virtual SpatialParentTree* getParentTree() const override;
const QUuid& getSelfID() const { return AVATAR_SELF_ID; }
public slots: public slots:
void increaseSize(); void increaseSize();
void decreaseSize(); void decreaseSize();
@ -648,8 +656,6 @@ private:
void setVisibleInSceneIfReady(Model* model, const render::ScenePointer& scene, bool visiblity); void setVisibleInSceneIfReady(Model* model, const render::ScenePointer& scene, bool visiblity);
private:
virtual void updatePalms() override {} virtual void updatePalms() override {}
void lateUpdatePalms(); void lateUpdatePalms();

View file

@ -105,19 +105,19 @@ RSA* readKeys(const char* filename) {
return key; return key;
} }
bool writeBackupInstructions() { bool Wallet::writeBackupInstructions() {
QString inputFilename(PathUtils::resourcesPath() + "html/commerce/backup_instructions.html"); QString inputFilename(PathUtils::resourcesPath() + "html/commerce/backup_instructions.html");
QString filename = PathUtils::getAppDataFilePath(INSTRUCTIONS_FILE); QString outputFilename = PathUtils::getAppDataFilePath(INSTRUCTIONS_FILE);
QFile outputFile(filename); QFile outputFile(outputFilename);
bool retval = false; bool retval = false;
if (QFile::exists(filename)) if (QFile::exists(outputFilename) || getKeyFilePath() == "")
{ {
QFile::remove(filename); return false;
} }
QFile::copy(inputFilename, filename); QFile::copy(inputFilename, outputFilename);
if (QFile::exists(filename) && outputFile.open(QIODevice::ReadWrite)) { if (QFile::exists(outputFilename) && outputFile.open(QIODevice::ReadWrite)) {
QByteArray fileData = outputFile.readAll(); QByteArray fileData = outputFile.readAll();
QString text(fileData); QString text(fileData);
@ -132,7 +132,7 @@ bool writeBackupInstructions() {
retval = true; retval = true;
qCDebug(commerce) << "wrote html file successfully"; qCDebug(commerce) << "wrote html file successfully";
} else { } else {
qCDebug(commerce) << "failed to open output html file" << filename; qCDebug(commerce) << "failed to open output html file" << outputFilename;
} }
return retval; return retval;
} }
@ -154,8 +154,6 @@ bool writeKeys(const char* filename, RSA* keys) {
QFile(QString(filename)).remove(); QFile(QString(filename)).remove();
return retval; return retval;
} }
writeBackupInstructions();
retval = true; retval = true;
qCDebug(commerce) << "wrote keys successfully"; qCDebug(commerce) << "wrote keys successfully";
@ -359,6 +357,8 @@ bool Wallet::setPassphrase(const QString& passphrase) {
_publicKeys.clear(); _publicKeys.clear();
writeBackupInstructions();
return true; return true;
} }
@ -526,6 +526,8 @@ bool Wallet::generateKeyPair() {
qCInfo(commerce) << "Generating keypair."; qCInfo(commerce) << "Generating keypair.";
auto keyPair = generateRSAKeypair(); auto keyPair = generateRSAKeypair();
writeBackupInstructions();
// TODO: redo this soon -- need error checking and so on // TODO: redo this soon -- need error checking and so on
writeSecurityImage(_securityImage, keyFilePath()); writeSecurityImage(_securityImage, keyFilePath());
QString oldKey = _publicKeys.count() == 0 ? "" : _publicKeys.last(); QString oldKey = _publicKeys.count() == 0 ? "" : _publicKeys.last();

View file

@ -80,6 +80,7 @@ private:
void updateImageProvider(); void updateImageProvider();
bool writeSecurityImage(const QPixmap* pixmap, const QString& outputFilePath); bool writeSecurityImage(const QPixmap* pixmap, const QString& outputFilePath);
bool readSecurityImage(const QString& inputFilePath, unsigned char** outputBufferPtr, int* outputBufferLen); bool readSecurityImage(const QString& inputFilePath, unsigned char** outputBufferPtr, int* outputBufferLen);
bool writeBackupInstructions();
bool verifyOwnerChallenge(const QByteArray& encryptedText, const QString& publicKey, QString& decryptedText); bool verifyOwnerChallenge(const QByteArray& encryptedText, const QString& publicKey, QString& decryptedText);

View file

@ -15,13 +15,14 @@
#include "avatar/AvatarManager.h" #include "avatar/AvatarManager.h"
LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates,
const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool enabled) : const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled) :
_renderingEnabled(enabled), _renderingEnabled(enabled),
_renderStates(renderStates), _renderStates(renderStates),
_defaultRenderStates(defaultRenderStates), _defaultRenderStates(defaultRenderStates),
_faceAvatar(faceAvatar), _faceAvatar(faceAvatar),
_centerEndY(centerEndY), _centerEndY(centerEndY),
_lockEnd(lockEnd) _lockEnd(lockEnd),
_distanceScaleEnd(distanceScaleEnd)
{ {
_rayPickUID = DependencyManager::get<RayPickScriptingInterface>()->createRayPick(rayProps); _rayPickUID = DependencyManager::get<RayPickScriptingInterface>()->createRayPick(rayProps);
@ -86,6 +87,10 @@ void LaserPointer::editRenderState(const std::string& state, const QVariant& sta
updateRenderStateOverlay(_renderStates[state].getStartID(), startProps); updateRenderStateOverlay(_renderStates[state].getStartID(), startProps);
updateRenderStateOverlay(_renderStates[state].getPathID(), pathProps); updateRenderStateOverlay(_renderStates[state].getPathID(), pathProps);
updateRenderStateOverlay(_renderStates[state].getEndID(), endProps); updateRenderStateOverlay(_renderStates[state].getEndID(), endProps);
QVariant endDim = endProps.toMap()["dimensions"];
if (endDim.isValid()) {
_renderStates[state].setEndDim(vec3FromVariant(endDim));
}
} }
void LaserPointer::updateRenderStateOverlay(const OverlayID& id, const QVariant& props) { void LaserPointer::updateRenderStateOverlay(const OverlayID& id, const QVariant& props) {
@ -154,10 +159,14 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter
if (!renderState.getEndID().isNull()) { if (!renderState.getEndID().isNull()) {
QVariantMap endProps; QVariantMap endProps;
glm::quat faceAvatarRotation = DependencyManager::get<AvatarManager>()->getMyAvatar()->getOrientation() * glm::quat(glm::radians(glm::vec3(0.0f, 180.0f, 0.0f))); glm::quat faceAvatarRotation = DependencyManager::get<AvatarManager>()->getMyAvatar()->getOrientation() * glm::quat(glm::radians(glm::vec3(0.0f, 180.0f, 0.0f)));
glm::vec3 dim = vec3FromVariant(qApp->getOverlays().getProperty(renderState.getEndID(), "dimensions").value);
if (_distanceScaleEnd) {
dim = renderState.getEndDim() * glm::distance(pickRay.origin, endVec) * DependencyManager::get<AvatarManager>()->getMyAvatar()->getSensorToWorldScale();
endProps.insert("dimensions", vec3toVariant(dim));
}
if (_centerEndY) { if (_centerEndY) {
endProps.insert("position", end); endProps.insert("position", end);
} else { } else {
glm::vec3 dim = vec3FromVariant(qApp->getOverlays().getProperty(renderState.getEndID(), "dimensions").value);
glm::vec3 currentUpVector = faceAvatarRotation * Vectors::UP; glm::vec3 currentUpVector = faceAvatarRotation * Vectors::UP;
endProps.insert("position", vec3toVariant(endVec + glm::vec3(currentUpVector.x * 0.5f * dim.y, currentUpVector.y * 0.5f * dim.y, currentUpVector.z * 0.5f * dim.y))); endProps.insert("position", vec3toVariant(endVec + glm::vec3(currentUpVector.x * 0.5f * dim.y, currentUpVector.y * 0.5f * dim.y, currentUpVector.z * 0.5f * dim.y)));
} }
@ -264,6 +273,7 @@ RenderState::RenderState(const OverlayID& startID, const OverlayID& pathID, cons
_pathIgnoreRays = qApp->getOverlays().getProperty(_pathID, "ignoreRayIntersection").value.toBool(); _pathIgnoreRays = qApp->getOverlays().getProperty(_pathID, "ignoreRayIntersection").value.toBool();
} }
if (!_endID.isNull()) { if (!_endID.isNull()) {
_endDim = vec3FromVariant(qApp->getOverlays().getProperty(_endID, "dimensions").value);
_endIgnoreRays = qApp->getOverlays().getProperty(_endID, "ignoreRayIntersection").value.toBool(); _endIgnoreRays = qApp->getOverlays().getProperty(_endID, "ignoreRayIntersection").value.toBool();
} }
} }

View file

@ -32,6 +32,9 @@ public:
const bool& doesPathIgnoreRays() const { return _pathIgnoreRays; } const bool& doesPathIgnoreRays() const { return _pathIgnoreRays; }
const bool& doesEndIgnoreRays() const { return _endIgnoreRays; } const bool& doesEndIgnoreRays() const { return _endIgnoreRays; }
void setEndDim(const glm::vec3& endDim) { _endDim = endDim; }
const glm::vec3& getEndDim() const { return _endDim; }
void deleteOverlays(); void deleteOverlays();
private: private:
@ -41,6 +44,8 @@ private:
bool _startIgnoreRays; bool _startIgnoreRays;
bool _pathIgnoreRays; bool _pathIgnoreRays;
bool _endIgnoreRays; bool _endIgnoreRays;
glm::vec3 _endDim;
}; };
@ -52,7 +57,7 @@ public:
typedef std::unordered_map<std::string, std::pair<float, RenderState>> DefaultRenderStateMap; typedef std::unordered_map<std::string, std::pair<float, RenderState>> DefaultRenderStateMap;
LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates,
const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool enabled); const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled);
~LaserPointer(); ~LaserPointer();
QUuid getRayUID() { return _rayPickUID; } QUuid getRayUID() { return _rayPickUID; }
@ -88,6 +93,7 @@ private:
bool _faceAvatar; bool _faceAvatar;
bool _centerEndY; bool _centerEndY;
bool _lockEnd; bool _lockEnd;
bool _distanceScaleEnd;
std::pair<QUuid, bool> _objectLockEnd { std::pair<QUuid, bool>(QUuid(), false)}; std::pair<QUuid, bool> _objectLockEnd { std::pair<QUuid, bool>(QUuid(), false)};
QUuid _rayPickUID; QUuid _rayPickUID;

View file

@ -11,8 +11,8 @@
#include "LaserPointerManager.h" #include "LaserPointerManager.h"
QUuid LaserPointerManager::createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates, QUuid LaserPointerManager::createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates,
const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool enabled) { const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled) {
std::shared_ptr<LaserPointer> laserPointer = std::make_shared<LaserPointer>(rayProps, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, enabled); std::shared_ptr<LaserPointer> laserPointer = std::make_shared<LaserPointer>(rayProps, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, enabled);
if (!laserPointer->getRayUID().isNull()) { if (!laserPointer->getRayUID().isNull()) {
QWriteLocker containsLock(&_containsLock); QWriteLocker containsLock(&_containsLock);
QUuid id = QUuid::createUuid(); QUuid id = QUuid::createUuid();

View file

@ -22,7 +22,7 @@ class LaserPointerManager {
public: public:
QUuid createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates, QUuid createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates,
const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool enabled); const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled);
void removeLaserPointer(const QUuid uid); void removeLaserPointer(const QUuid uid);
void enableLaserPointer(const QUuid uid); void enableLaserPointer(const QUuid uid);
void disableLaserPointer(const QUuid uid); void disableLaserPointer(const QUuid uid);

View file

@ -32,6 +32,11 @@ QUuid LaserPointerScriptingInterface::createLaserPointer(const QVariant& propert
lockEnd = propertyMap["lockEnd"].toBool(); lockEnd = propertyMap["lockEnd"].toBool();
} }
bool distanceScaleEnd = false;
if (propertyMap["distanceScaleEnd"].isValid()) {
distanceScaleEnd = propertyMap["distanceScaleEnd"].toBool();
}
bool enabled = false; bool enabled = false;
if (propertyMap["enabled"].isValid()) { if (propertyMap["enabled"].isValid()) {
enabled = propertyMap["enabled"].toBool(); enabled = propertyMap["enabled"].toBool();
@ -66,7 +71,7 @@ QUuid LaserPointerScriptingInterface::createLaserPointer(const QVariant& propert
} }
} }
return qApp->getLaserPointerManager().createLaserPointer(properties, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, enabled); return qApp->getLaserPointerManager().createLaserPointer(properties, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, enabled);
} }
void LaserPointerScriptingInterface::editRenderState(QUuid uid, const QString& renderState, const QVariant& properties) { void LaserPointerScriptingInterface::editRenderState(QUuid uid, const QString& renderState, const QVariant& properties) {

View file

@ -994,10 +994,12 @@ glm::quat Avatar::getAbsoluteJointRotationInObjectFrame(int index) const {
glm::mat4 finalMat = glm::inverse(avatarMatrix) * sensorToWorldMatrix; glm::mat4 finalMat = glm::inverse(avatarMatrix) * sensorToWorldMatrix;
return glmExtractRotation(finalMat); return glmExtractRotation(finalMat);
} }
case CAMERA_RELATIVE_CONTROLLER_LEFTHAND_INDEX:
case CONTROLLER_LEFTHAND_INDEX: { case CONTROLLER_LEFTHAND_INDEX: {
Transform controllerLeftHandTransform = Transform(getControllerLeftHandMatrix()); Transform controllerLeftHandTransform = Transform(getControllerLeftHandMatrix());
return controllerLeftHandTransform.getRotation(); return controllerLeftHandTransform.getRotation();
} }
case CAMERA_RELATIVE_CONTROLLER_RIGHTHAND_INDEX:
case CONTROLLER_RIGHTHAND_INDEX: { case CONTROLLER_RIGHTHAND_INDEX: {
Transform controllerRightHandTransform = Transform(getControllerRightHandMatrix()); Transform controllerRightHandTransform = Transform(getControllerRightHandMatrix());
return controllerRightHandTransform.getRotation(); return controllerRightHandTransform.getRotation();
@ -1032,10 +1034,12 @@ glm::vec3 Avatar::getAbsoluteJointTranslationInObjectFrame(int index) const {
glm::mat4 finalMat = glm::inverse(avatarMatrix) * sensorToWorldMatrix; glm::mat4 finalMat = glm::inverse(avatarMatrix) * sensorToWorldMatrix;
return extractTranslation(finalMat); return extractTranslation(finalMat);
} }
case CAMERA_RELATIVE_CONTROLLER_LEFTHAND_INDEX:
case CONTROLLER_LEFTHAND_INDEX: { case CONTROLLER_LEFTHAND_INDEX: {
Transform controllerLeftHandTransform = Transform(getControllerLeftHandMatrix()); Transform controllerLeftHandTransform = Transform(getControllerLeftHandMatrix());
return controllerLeftHandTransform.getTranslation(); return controllerLeftHandTransform.getTranslation();
} }
case CAMERA_RELATIVE_CONTROLLER_RIGHTHAND_INDEX:
case CONTROLLER_RIGHTHAND_INDEX: { case CONTROLLER_RIGHTHAND_INDEX: {
Transform controllerRightHandTransform = Transform(getControllerRightHandMatrix()); Transform controllerRightHandTransform = Transform(getControllerRightHandMatrix());
return controllerRightHandTransform.getTranslation(); return controllerRightHandTransform.getTranslation();

View file

@ -96,6 +96,7 @@ PolyLineEntityRenderer::PolyLineEntityRenderer(const EntityItemPointer& entity)
polylineFormat->setAttribute(gpu::Stream::POSITION, 0, gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ), offsetof(Vertex, position)); polylineFormat->setAttribute(gpu::Stream::POSITION, 0, gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ), offsetof(Vertex, position));
polylineFormat->setAttribute(gpu::Stream::NORMAL, 0, gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ), offsetof(Vertex, normal)); polylineFormat->setAttribute(gpu::Stream::NORMAL, 0, gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ), offsetof(Vertex, normal));
polylineFormat->setAttribute(gpu::Stream::TEXCOORD, 0, gpu::Element(gpu::VEC2, gpu::FLOAT, gpu::UV), offsetof(Vertex, uv)); polylineFormat->setAttribute(gpu::Stream::TEXCOORD, 0, gpu::Element(gpu::VEC2, gpu::FLOAT, gpu::UV), offsetof(Vertex, uv));
polylineFormat->setAttribute(gpu::Stream::COLOR, 0, gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::RGB), offsetof(Vertex, color));
}); });
PolyLineUniforms uniforms; PolyLineUniforms uniforms;
@ -116,7 +117,8 @@ bool PolyLineEntityRenderer::needsRenderUpdateFromTypedEntity(const TypedEntityP
entity->pointsChanged() || entity->pointsChanged() ||
entity->strokeWidthsChanged() || entity->strokeWidthsChanged() ||
entity->normalsChanged() || entity->normalsChanged() ||
entity->texturesChanged() entity->texturesChanged() ||
entity->strokeColorsChanged()
); );
} }
@ -129,9 +131,11 @@ void PolyLineEntityRenderer::doRenderUpdateSynchronousTyped(const ScenePointer&
if (!textures.isEmpty()) { if (!textures.isEmpty()) {
entityTextures = QUrl(textures); entityTextures = QUrl(textures);
} }
_texture = DependencyManager::get<TextureCache>()->getTexture(entityTextures);
} }
if (!_texture || _texture->getURL() != entityTextures) {
if (!_texture) {
_texture = DependencyManager::get<TextureCache>()->getTexture(entityTextures); _texture = DependencyManager::get<TextureCache>()->getTexture(entityTextures);
} }
} }
@ -143,6 +147,10 @@ void PolyLineEntityRenderer::doRenderUpdateAsynchronousTyped(const TypedEntityPo
auto pointsChanged = entity->pointsChanged(); auto pointsChanged = entity->pointsChanged();
auto strokeWidthsChanged = entity->strokeWidthsChanged(); auto strokeWidthsChanged = entity->strokeWidthsChanged();
auto normalsChanged = entity->normalsChanged(); auto normalsChanged = entity->normalsChanged();
auto strokeColorsChanged = entity->strokeColorsChanged();
bool isUVModeStretch = entity->getIsUVModeStretch();
entity->resetPolyLineChanged(); entity->resetPolyLineChanged();
_polylineTransform = Transform(); _polylineTransform = Transform();
@ -158,10 +166,14 @@ void PolyLineEntityRenderer::doRenderUpdateAsynchronousTyped(const TypedEntityPo
if (normalsChanged) { if (normalsChanged) {
_lastNormals = entity->getNormals(); _lastNormals = entity->getNormals();
} }
if (pointsChanged || strokeWidthsChanged || normalsChanged) { if (strokeColorsChanged) {
_lastStrokeColors = entity->getStrokeColors();
_lastStrokeColors = _lastNormals.size() == _lastStrokeColors.size() ? _lastStrokeColors : QVector<glm::vec3>({ toGlm(entity->getXColor()) });
}
if (pointsChanged || strokeWidthsChanged || normalsChanged || strokeColorsChanged) {
_empty = std::min(_lastPoints.size(), std::min(_lastNormals.size(), _lastStrokeWidths.size())) < 2; _empty = std::min(_lastPoints.size(), std::min(_lastNormals.size(), _lastStrokeWidths.size())) < 2;
if (!_empty) { if (!_empty) {
updateGeometry(updateVertices(_lastPoints, _lastNormals, _lastStrokeWidths)); updateGeometry(updateVertices(_lastPoints, _lastNormals, _lastStrokeWidths, _lastStrokeColors, isUVModeStretch, _textureAspectRatio));
} }
} }
} }
@ -175,7 +187,12 @@ void PolyLineEntityRenderer::updateGeometry(const std::vector<Vertex>& vertices)
_verticesBuffer->setSubData(0, vertices); _verticesBuffer->setSubData(0, vertices);
} }
std::vector<PolyLineEntityRenderer::Vertex> PolyLineEntityRenderer::updateVertices(const QVector<glm::vec3>& points, const QVector<glm::vec3>& normals, const QVector<float>& strokeWidths) { std::vector<PolyLineEntityRenderer::Vertex> PolyLineEntityRenderer::updateVertices(const QVector<glm::vec3>& points,
const QVector<glm::vec3>& normals,
const QVector<float>& strokeWidths,
const QVector<glm::vec3>& strokeColors,
const bool isUVModeStretch,
const float textureAspectRatio) {
// Calculate the minimum vector size out of normals, points, and stroke widths // Calculate the minimum vector size out of normals, points, and stroke widths
int size = std::min(points.size(), std::min(normals.size(), strokeWidths.size())); int size = std::min(points.size(), std::min(normals.size(), strokeWidths.size()));
@ -190,10 +207,52 @@ std::vector<PolyLineEntityRenderer::Vertex> PolyLineEntityRenderer::updateVertic
float uCoord = 0.0f; float uCoord = 0.0f;
int finalIndex = size - 1; int finalIndex = size - 1;
glm::vec3 binormal; glm::vec3 binormal;
float accumulatedDistance = 0.0f;
float distanceToLastPoint = 0.0f;
float accumulatedStrokeWidth = 0.0f;
float strokeWidth = 0.0f;
bool doesStrokeWidthVary = false;
for (int i = 1; i < strokeWidths.size(); i++) {
if (strokeWidths[i] != strokeWidths[i - 1]) {
doesStrokeWidthVary = true;
break;
}
}
for (int i = 0; i <= finalIndex; i++) { for (int i = 0; i <= finalIndex; i++) {
const float& width = strokeWidths.at(i); const float& width = strokeWidths.at(i);
const auto& point = points.at(i); const auto& point = points.at(i);
const auto& normal = normals.at(i); const auto& normal = normals.at(i);
const auto& color = strokeColors.size() == normals.size() ? strokeColors.at(i) : strokeColors.at(0);
int vertexIndex = i * 2;
if (!isUVModeStretch && i >= 1) {
distanceToLastPoint = glm::distance(points.at(i), points.at(i - 1));
accumulatedDistance += distanceToLastPoint;
strokeWidth = 2 * strokeWidths[i];
if (doesStrokeWidthVary) {
//If the stroke varies along the line the texture will stretch more or less depending on the speed
//because it looks better than using the same method as below
accumulatedStrokeWidth += strokeWidth;
float increaseValue = 1;
if (accumulatedStrokeWidth != 0) {
float newUcoord = glm::ceil(((1.0f / textureAspectRatio) * accumulatedDistance) / (accumulatedStrokeWidth / i));
increaseValue = newUcoord - uCoord;
}
increaseValue = increaseValue > 0 ? increaseValue : 1;
uCoord += increaseValue;
} else {
//If the stroke width is constant then the textures should keep the aspect ratio along the line
uCoord = ((1.0f / textureAspectRatio) * accumulatedDistance) / strokeWidth;
}
} else if (vertexIndex >= 2) {
uCoord += uCoordInc;
}
// For last point we can assume binormals are the same since it represents the last two vertices of quad // For last point we can assume binormals are the same since it represents the last two vertices of quad
if (i < finalIndex) { if (i < finalIndex) {
@ -206,11 +265,10 @@ std::vector<PolyLineEntityRenderer::Vertex> PolyLineEntityRenderer::updateVertic
} }
} }
const auto v1 = point + binormal; const auto v1 = points.at(i) + binormal;
const auto v2 = point - binormal; const auto v2 = points.at(i) - binormal;
vertices.emplace_back(v1, normal, vec2(uCoord, 0.0f)); vertices.emplace_back(v1, normal, vec2(uCoord, 0.0f), color);
vertices.emplace_back(v2, normal, vec2(uCoord, 1.0f)); vertices.emplace_back(v2, normal, vec2(uCoord, 1.0f), color);
uCoord += uCoordInc;
} }
return vertices; return vertices;
@ -235,6 +293,12 @@ void PolyLineEntityRenderer::doRender(RenderArgs* args) {
batch.setResourceTexture(PAINTSTROKE_TEXTURE_SLOT, DependencyManager::get<TextureCache>()->getWhiteTexture()); batch.setResourceTexture(PAINTSTROKE_TEXTURE_SLOT, DependencyManager::get<TextureCache>()->getWhiteTexture());
} }
float textureWidth = (float)_texture->getOriginalWidth();
float textureHeight = (float)_texture->getOriginalHeight();
if (textureWidth != 0 && textureHeight != 0) {
_textureAspectRatio = textureWidth / textureHeight;
}
batch.setInputFormat(polylineFormat); batch.setInputFormat(polylineFormat);
batch.setInputBuffer(0, _verticesBuffer, 0, sizeof(Vertex)); batch.setInputBuffer(0, _verticesBuffer, 0, sizeof(Vertex));
@ -247,4 +311,4 @@ void PolyLineEntityRenderer::doRender(RenderArgs* args) {
#endif #endif
batch.draw(gpu::TRIANGLE_STRIP, _numVertices, 0); batch.draw(gpu::TRIANGLE_STRIP, _numVertices, 0);
} }

View file

@ -27,7 +27,9 @@ public:
protected: protected:
virtual bool needsRenderUpdateFromTypedEntity(const TypedEntityPointer& entity) const override; virtual bool needsRenderUpdateFromTypedEntity(const TypedEntityPointer& entity) const override;
virtual void doRenderUpdateSynchronousTyped(const ScenePointer& scene, Transaction& transaction, const TypedEntityPointer& entity) override; virtual void doRenderUpdateSynchronousTyped(const ScenePointer& scene,
Transaction& transaction,
const TypedEntityPointer& entity) override;
virtual void doRenderUpdateAsynchronousTyped(const TypedEntityPointer& entity) override; virtual void doRenderUpdateAsynchronousTyped(const TypedEntityPointer& entity) override;
virtual ItemKey getKey() override; virtual ItemKey getKey() override;
@ -38,24 +40,37 @@ protected:
struct Vertex { struct Vertex {
Vertex() {} Vertex() {}
Vertex(const vec3& position, const vec3& normal, const vec2& uv) : position(position), normal(normal), uv(uv) {} Vertex(const vec3& position, const vec3& normal, const vec2& uv, const vec3& color) : position(position),
normal(normal),
uv(uv),
color(color) {}
vec3 position; vec3 position;
vec3 normal; vec3 normal;
vec2 uv; vec2 uv;
vec3 color;
}; };
void updateGeometry(const std::vector<Vertex>& vertices); void updateGeometry(const std::vector<Vertex>& vertices);
static std::vector<Vertex> updateVertices(const QVector<glm::vec3>& points, const QVector<glm::vec3>& normals, const QVector<float>& strokeWidths); static std::vector<Vertex> updateVertices(const QVector<glm::vec3>& points,
const QVector<glm::vec3>& normals,
const QVector<float>& strokeWidths,
const QVector<glm::vec3>& strokeColors,
const bool isUVModeStretch,
const float textureAspectRatio);
Transform _polylineTransform; Transform _polylineTransform;
QVector<glm::vec3> _lastPoints; QVector<glm::vec3> _lastPoints;
QVector<glm::vec3> _lastNormals; QVector<glm::vec3> _lastNormals;
QVector<glm::vec3> _lastStrokeColors;
QVector<float> _lastStrokeWidths; QVector<float> _lastStrokeWidths;
gpu::BufferPointer _verticesBuffer; gpu::BufferPointer _verticesBuffer;
gpu::BufferView _uniformBuffer; gpu::BufferView _uniformBuffer;
uint32_t _numVertices { 0 }; uint32_t _numVertices { 0 };
bool _empty{ true }; bool _empty{ true };
NetworkTexturePointer _texture; NetworkTexturePointer _texture;
float _textureAspectRatio { 1.0f };
}; };
} } // namespace } } // namespace

View file

@ -40,7 +40,7 @@ void main(void) {
packDeferredFragmentTranslucent( packDeferredFragmentTranslucent(
float(frontCondition) * interpolatedNormal, float(frontCondition) * interpolatedNormal,
texel.a * varColor.a, texel.a * varColor.a,
polyline.color * texel.rgb, color * texel.rgb,
vec3(0.01, 0.01, 0.01), vec3(0.01, 0.01, 0.01),
10.0); 10.0);
} }

View file

@ -355,7 +355,9 @@ EntityPropertyFlags EntityItemProperties::getChangedProperties() const {
CHECK_PROPERTY_CHANGE(PROP_FACE_CAMERA, faceCamera); CHECK_PROPERTY_CHANGE(PROP_FACE_CAMERA, faceCamera);
CHECK_PROPERTY_CHANGE(PROP_ACTION_DATA, actionData); CHECK_PROPERTY_CHANGE(PROP_ACTION_DATA, actionData);
CHECK_PROPERTY_CHANGE(PROP_NORMALS, normals); CHECK_PROPERTY_CHANGE(PROP_NORMALS, normals);
CHECK_PROPERTY_CHANGE(PROP_STROKE_COLORS, strokeColors);
CHECK_PROPERTY_CHANGE(PROP_STROKE_WIDTHS, strokeWidths); CHECK_PROPERTY_CHANGE(PROP_STROKE_WIDTHS, strokeWidths);
CHECK_PROPERTY_CHANGE(PROP_IS_UV_MODE_STRETCH, isUVModeStretch);
CHECK_PROPERTY_CHANGE(PROP_X_TEXTURE_URL, xTextureURL); CHECK_PROPERTY_CHANGE(PROP_X_TEXTURE_URL, xTextureURL);
CHECK_PROPERTY_CHANGE(PROP_Y_TEXTURE_URL, yTextureURL); CHECK_PROPERTY_CHANGE(PROP_Y_TEXTURE_URL, yTextureURL);
CHECK_PROPERTY_CHANGE(PROP_Z_TEXTURE_URL, zTextureURL); CHECK_PROPERTY_CHANGE(PROP_Z_TEXTURE_URL, zTextureURL);
@ -605,8 +607,10 @@ QScriptValue EntityItemProperties::copyToScriptValue(QScriptEngine* engine, bool
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LINE_WIDTH, lineWidth); COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LINE_WIDTH, lineWidth);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LINE_POINTS, linePoints); COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_LINE_POINTS, linePoints);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_NORMALS, normals); COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_NORMALS, normals);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_STROKE_COLORS, strokeColors);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_STROKE_WIDTHS, strokeWidths); COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_STROKE_WIDTHS, strokeWidths);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_TEXTURES, textures); COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_TEXTURES, textures);
COPY_PROPERTY_TO_QSCRIPTVALUE(PROP_IS_UV_MODE_STRETCH, isUVModeStretch);
} }
if (!skipDefaults && !strictSemantics) { if (!skipDefaults && !strictSemantics) {
@ -771,7 +775,10 @@ void EntityItemProperties::copyFromScriptValue(const QScriptValue& object, bool
COPY_PROPERTY_FROM_QSCRIPTVALUE(faceCamera, bool, setFaceCamera); COPY_PROPERTY_FROM_QSCRIPTVALUE(faceCamera, bool, setFaceCamera);
COPY_PROPERTY_FROM_QSCRIPTVALUE(actionData, QByteArray, setActionData); COPY_PROPERTY_FROM_QSCRIPTVALUE(actionData, QByteArray, setActionData);
COPY_PROPERTY_FROM_QSCRIPTVALUE(normals, qVectorVec3, setNormals); COPY_PROPERTY_FROM_QSCRIPTVALUE(normals, qVectorVec3, setNormals);
COPY_PROPERTY_FROM_QSCRIPTVALUE(strokeColors, qVectorVec3, setStrokeColors);
COPY_PROPERTY_FROM_QSCRIPTVALUE(strokeWidths,qVectorFloat, setStrokeWidths); COPY_PROPERTY_FROM_QSCRIPTVALUE(strokeWidths,qVectorFloat, setStrokeWidths);
COPY_PROPERTY_FROM_QSCRIPTVALUE(isUVModeStretch, bool, setIsUVModeStretch);
if (!honorReadOnly) { if (!honorReadOnly) {
// this is used by the json reader to set things that we don't want javascript to able to affect. // this is used by the json reader to set things that we don't want javascript to able to affect.
@ -925,7 +932,9 @@ void EntityItemProperties::merge(const EntityItemProperties& other) {
COPY_PROPERTY_IF_CHANGED(faceCamera); COPY_PROPERTY_IF_CHANGED(faceCamera);
COPY_PROPERTY_IF_CHANGED(actionData); COPY_PROPERTY_IF_CHANGED(actionData);
COPY_PROPERTY_IF_CHANGED(normals); COPY_PROPERTY_IF_CHANGED(normals);
COPY_PROPERTY_IF_CHANGED(strokeColors);
COPY_PROPERTY_IF_CHANGED(strokeWidths); COPY_PROPERTY_IF_CHANGED(strokeWidths);
COPY_PROPERTY_IF_CHANGED(isUVModeStretch);
COPY_PROPERTY_IF_CHANGED(created); COPY_PROPERTY_IF_CHANGED(created);
_animation.merge(other._animation); _animation.merge(other._animation);
@ -1112,7 +1121,9 @@ void EntityItemProperties::entityPropertyFlagsFromScriptValue(const QScriptValue
ADD_PROPERTY_TO_MAP(PROP_FACE_CAMERA, FaceCamera, faceCamera, bool); ADD_PROPERTY_TO_MAP(PROP_FACE_CAMERA, FaceCamera, faceCamera, bool);
ADD_PROPERTY_TO_MAP(PROP_ACTION_DATA, ActionData, actionData, QByteArray); ADD_PROPERTY_TO_MAP(PROP_ACTION_DATA, ActionData, actionData, QByteArray);
ADD_PROPERTY_TO_MAP(PROP_NORMALS, Normals, normals, QVector<glm::vec3>); ADD_PROPERTY_TO_MAP(PROP_NORMALS, Normals, normals, QVector<glm::vec3>);
ADD_PROPERTY_TO_MAP(PROP_STROKE_COLORS, StrokeColors, strokeColors, QVector<glm::vec3>);
ADD_PROPERTY_TO_MAP(PROP_STROKE_WIDTHS, StrokeWidths, strokeWidths, QVector<float>); ADD_PROPERTY_TO_MAP(PROP_STROKE_WIDTHS, StrokeWidths, strokeWidths, QVector<float>);
ADD_PROPERTY_TO_MAP(PROP_IS_UV_MODE_STRETCH, IsUVModeStretch, isUVModeStretch, QVector<float>);
ADD_PROPERTY_TO_MAP(PROP_X_TEXTURE_URL, XTextureURL, xTextureURL, QString); ADD_PROPERTY_TO_MAP(PROP_X_TEXTURE_URL, XTextureURL, xTextureURL, QString);
ADD_PROPERTY_TO_MAP(PROP_Y_TEXTURE_URL, YTextureURL, yTextureURL, QString); ADD_PROPERTY_TO_MAP(PROP_Y_TEXTURE_URL, YTextureURL, yTextureURL, QString);
ADD_PROPERTY_TO_MAP(PROP_Z_TEXTURE_URL, ZTextureURL, zTextureURL, QString); ADD_PROPERTY_TO_MAP(PROP_Z_TEXTURE_URL, ZTextureURL, zTextureURL, QString);
@ -1458,9 +1469,11 @@ bool EntityItemProperties::encodeEntityEditPacket(PacketType command, EntityItem
if (properties.getType() == EntityTypes::PolyLine) { if (properties.getType() == EntityTypes::PolyLine) {
APPEND_ENTITY_PROPERTY(PROP_LINE_WIDTH, properties.getLineWidth()); APPEND_ENTITY_PROPERTY(PROP_LINE_WIDTH, properties.getLineWidth());
APPEND_ENTITY_PROPERTY(PROP_LINE_POINTS, properties.getLinePoints()); APPEND_ENTITY_PROPERTY(PROP_LINE_POINTS, properties.getLinePoints());
APPEND_ENTITY_PROPERTY(PROP_NORMALS, properties.getNormals()); APPEND_ENTITY_PROPERTY(PROP_NORMALS, properties.getPackedNormals());
APPEND_ENTITY_PROPERTY(PROP_STROKE_COLORS, properties.getPackedStrokeColors());
APPEND_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, properties.getStrokeWidths()); APPEND_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, properties.getStrokeWidths());
APPEND_ENTITY_PROPERTY(PROP_TEXTURES, properties.getTextures()); APPEND_ENTITY_PROPERTY(PROP_TEXTURES, properties.getTextures());
APPEND_ENTITY_PROPERTY(PROP_IS_UV_MODE_STRETCH, properties.getIsUVModeStretch());
} }
// NOTE: Spheres and Boxes are just special cases of Shape, and they need to include their PROP_SHAPE // NOTE: Spheres and Boxes are just special cases of Shape, and they need to include their PROP_SHAPE
// when encoding/decoding edits because otherwise they can't polymorph to other shape types // when encoding/decoding edits because otherwise they can't polymorph to other shape types
@ -1547,6 +1560,44 @@ bool EntityItemProperties::encodeEntityEditPacket(PacketType command, EntityItem
return success; return success;
} }
QByteArray EntityItemProperties::getPackedNormals() const {
return packNormals(getNormals());
}
QByteArray EntityItemProperties::packNormals(const QVector<glm::vec3>& normals) const {
int normalsSize = normals.size();
QByteArray packedNormals = QByteArray(normalsSize * 6 + 1, '0');
// add size of the array
packedNormals[0] = ((uint8_t)normalsSize);
int index = 1;
for (int i = 0; i < normalsSize; i++) {
int numBytes = packFloatVec3ToSignedTwoByteFixed((unsigned char*)packedNormals.data() + index, normals[i], 15);
index += numBytes;
}
return packedNormals;
}
QByteArray EntityItemProperties::getPackedStrokeColors() const {
return packStrokeColors(getStrokeColors());
}
QByteArray EntityItemProperties::packStrokeColors(const QVector<glm::vec3>& strokeColors) const {
int strokeColorsSize = strokeColors.size();
QByteArray packedStrokeColors = QByteArray(strokeColorsSize * 3 + 1, '0');
// add size of the array
packedStrokeColors[0] = ((uint8_t)strokeColorsSize);
for (int i = 0; i < strokeColorsSize; i++) {
// add the color to the QByteArray
packedStrokeColors[i * 3 + 1] = strokeColors[i].r * 255;
packedStrokeColors[i * 3 + 2] = strokeColors[i].g * 255;
packedStrokeColors[i * 3 + 3] = strokeColors[i].b * 255;
}
return packedStrokeColors;
}
// TODO: // TODO:
// how to handle lastEdited? // how to handle lastEdited?
// how to handle lastUpdated? // how to handle lastUpdated?
@ -1768,9 +1819,11 @@ bool EntityItemProperties::decodeEntityEditPacket(const unsigned char* data, int
if (properties.getType() == EntityTypes::PolyLine) { if (properties.getType() == EntityTypes::PolyLine) {
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_LINE_WIDTH, float, setLineWidth); READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_LINE_WIDTH, float, setLineWidth);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_LINE_POINTS, QVector<glm::vec3>, setLinePoints); READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_LINE_POINTS, QVector<glm::vec3>, setLinePoints);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_NORMALS, QVector<glm::vec3>, setNormals); READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_NORMALS, QByteArray, setPackedNormals);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_STROKE_COLORS, QByteArray, setPackedStrokeColors);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_STROKE_WIDTHS, QVector<float>, setStrokeWidths); READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_STROKE_WIDTHS, QVector<float>, setStrokeWidths);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_TEXTURES, QString, setTextures); READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_TEXTURES, QString, setTextures);
READ_ENTITY_PROPERTY_TO_PROPERTIES(PROP_IS_UV_MODE_STRETCH, bool, setIsUVModeStretch);
} }
// NOTE: Spheres and Boxes are just special cases of Shape, and they need to include their PROP_SHAPE // NOTE: Spheres and Boxes are just special cases of Shape, and they need to include their PROP_SHAPE
@ -1801,6 +1854,53 @@ bool EntityItemProperties::decodeEntityEditPacket(const unsigned char* data, int
return valid; return valid;
} }
void EntityItemProperties::setPackedNormals(const QByteArray& value) {
setNormals(unpackNormals(value));
}
QVector<glm::vec3> EntityItemProperties::unpackNormals(const QByteArray& normals) {
// the size of the vector is packed first
QVector<glm::vec3> unpackedNormals = QVector<glm::vec3>((int)normals[0]);
if ((int)normals[0] == normals.size() / 6) {
int j = 0;
for (int i = 1; i < normals.size();) {
glm::vec3 aux = glm::vec3();
i += unpackFloatVec3FromSignedTwoByteFixed((unsigned char*)normals.data() + i, aux, 15);
unpackedNormals[j] = aux;
j++;
}
} else {
qCDebug(entities) << "WARNING - Expected received size for normals does not match. Expected: " << (int)normals[0]
<< " Received: " << (normals.size() / 6);
}
return unpackedNormals;
}
void EntityItemProperties::setPackedStrokeColors(const QByteArray& value) {
setStrokeColors(unpackStrokeColors(value));
}
QVector<glm::vec3> EntityItemProperties::unpackStrokeColors(const QByteArray& strokeColors) {
// the size of the vector is packed first
QVector<glm::vec3> unpackedStrokeColors = QVector<glm::vec3>((int)strokeColors[0]);
if ((int)strokeColors[0] == strokeColors.size() / 3) {
int j = 0;
for (int i = 1; i < strokeColors.size();) {
float r = (uint8_t)strokeColors[i++] / 255.0f;
float g = (uint8_t)strokeColors[i++] / 255.0f;
float b = (uint8_t)strokeColors[i++] / 255.0f;
unpackedStrokeColors[j++] = glmVec3(r, g, b);
}
} else {
qCDebug(entities) << "WARNING - Expected received size for stroke colors does not match. Expected: "
<< (int)strokeColors[0] << " Received: " << (strokeColors.size() / 3);
}
return unpackedStrokeColors;
}
// NOTE: This version will only encode the portion of the edit message immediately following the // NOTE: This version will only encode the portion of the edit message immediately following the
// header it does not include the send times and sequence number because that is handled by the // header it does not include the send times and sequence number because that is handled by the
@ -1942,7 +2042,9 @@ void EntityItemProperties::markAllChanged() {
_actionDataChanged = true; _actionDataChanged = true;
_normalsChanged = true; _normalsChanged = true;
_strokeColorsChanged = true;
_strokeWidthsChanged = true; _strokeWidthsChanged = true;
_isUVModeStretchChanged = true;
_xTextureURLChanged = true; _xTextureURLChanged = true;
_yTextureURLChanged = true; _yTextureURLChanged = true;
@ -2357,6 +2459,14 @@ QList<QString> EntityItemProperties::listChangedProperties() {
out += "shape"; out += "shape";
} }
if (strokeColorsChanged()) {
out += "strokeColors";
}
if (isUVModeStretchChanged()) {
out += "isUVModeStretch";
}
getAnimation().listChangedProperties(out); getAnimation().listChangedProperties(out);
getKeyLight().listChangedProperties(out); getKeyLight().listChangedProperties(out);
getSkybox().listChangedProperties(out); getSkybox().listChangedProperties(out);

View file

@ -191,8 +191,10 @@ public:
DEFINE_PROPERTY_REF(PROP_DESCRIPTION, Description, description, QString, ""); DEFINE_PROPERTY_REF(PROP_DESCRIPTION, Description, description, QString, "");
DEFINE_PROPERTY(PROP_FACE_CAMERA, FaceCamera, faceCamera, bool, TextEntityItem::DEFAULT_FACE_CAMERA); DEFINE_PROPERTY(PROP_FACE_CAMERA, FaceCamera, faceCamera, bool, TextEntityItem::DEFAULT_FACE_CAMERA);
DEFINE_PROPERTY_REF(PROP_ACTION_DATA, ActionData, actionData, QByteArray, QByteArray()); DEFINE_PROPERTY_REF(PROP_ACTION_DATA, ActionData, actionData, QByteArray, QByteArray());
DEFINE_PROPERTY(PROP_NORMALS, Normals, normals, QVector<glm::vec3>, QVector<glm::vec3>()); DEFINE_PROPERTY(PROP_NORMALS, Normals, normals, QVector<glm::vec3>, ENTITY_ITEM_DEFAULT_EMPTY_VEC3_QVEC);
DEFINE_PROPERTY(PROP_STROKE_COLORS, StrokeColors, strokeColors, QVector<glm::vec3>, ENTITY_ITEM_DEFAULT_EMPTY_VEC3_QVEC);
DEFINE_PROPERTY(PROP_STROKE_WIDTHS, StrokeWidths, strokeWidths, QVector<float>, QVector<float>()); DEFINE_PROPERTY(PROP_STROKE_WIDTHS, StrokeWidths, strokeWidths, QVector<float>, QVector<float>());
DEFINE_PROPERTY(PROP_IS_UV_MODE_STRETCH, IsUVModeStretch, isUVModeStretch, bool, true);
DEFINE_PROPERTY_REF(PROP_X_TEXTURE_URL, XTextureURL, xTextureURL, QString, ""); DEFINE_PROPERTY_REF(PROP_X_TEXTURE_URL, XTextureURL, xTextureURL, QString, "");
DEFINE_PROPERTY_REF(PROP_Y_TEXTURE_URL, YTextureURL, yTextureURL, QString, ""); DEFINE_PROPERTY_REF(PROP_Y_TEXTURE_URL, YTextureURL, yTextureURL, QString, "");
DEFINE_PROPERTY_REF(PROP_Z_TEXTURE_URL, ZTextureURL, zTextureURL, QString, ""); DEFINE_PROPERTY_REF(PROP_Z_TEXTURE_URL, ZTextureURL, zTextureURL, QString, "");
@ -322,6 +324,17 @@ public:
bool getRenderInfoHasTransparent() const { return _renderInfoHasTransparent; } bool getRenderInfoHasTransparent() const { return _renderInfoHasTransparent; }
void setRenderInfoHasTransparent(bool value) { _renderInfoHasTransparent = value; } void setRenderInfoHasTransparent(bool value) { _renderInfoHasTransparent = value; }
void setPackedNormals(const QByteArray& value);
QVector<glm::vec3> unpackNormals(const QByteArray& normals);
void setPackedStrokeColors(const QByteArray& value);
QVector<glm::vec3> unpackStrokeColors(const QByteArray& strokeColors);
QByteArray getPackedNormals() const;
QByteArray packNormals(const QVector<glm::vec3>& normals) const;
QByteArray getPackedStrokeColors() const;
QByteArray packStrokeColors(const QVector<glm::vec3>& strokeColors) const;
protected: protected:
QString getCollisionMaskAsString() const; QString getCollisionMaskAsString() const;

View file

@ -24,6 +24,8 @@ const glm::vec3 ENTITY_ITEM_ZERO_VEC3 = glm::vec3(0.0f);
const glm::vec3 ENTITY_ITEM_ONE_VEC3 = glm::vec3(1.0f); const glm::vec3 ENTITY_ITEM_ONE_VEC3 = glm::vec3(1.0f);
const glm::vec3 ENTITY_ITEM_HALF_VEC3 = glm::vec3(0.5f); const glm::vec3 ENTITY_ITEM_HALF_VEC3 = glm::vec3(0.5f);
const QVector<glm::vec3> ENTITY_ITEM_DEFAULT_EMPTY_VEC3_QVEC = QVector<glm::vec3>();
const bool ENTITY_ITEM_DEFAULT_LOCKED = false; const bool ENTITY_ITEM_DEFAULT_LOCKED = false;
const QString ENTITY_ITEM_DEFAULT_USER_DATA = QString(""); const QString ENTITY_ITEM_DEFAULT_USER_DATA = QString("");
const QUuid ENTITY_ITEM_DEFAULT_SIMULATOR_ID = QUuid(); const QUuid ENTITY_ITEM_DEFAULT_SIMULATOR_ID = QUuid();

View file

@ -109,7 +109,9 @@ enum EntityPropertyList {
// Used by PolyLine entity // Used by PolyLine entity
PROP_NORMALS, PROP_NORMALS,
PROP_STROKE_COLORS,
PROP_STROKE_WIDTHS, PROP_STROKE_WIDTHS,
PROP_IS_UV_MODE_STRETCH,
// used by particles // used by particles
PROP_SPEED_SPREAD, PROP_SPEED_SPREAD,

View file

@ -22,7 +22,7 @@
#include "PolyLineEntityItem.h" #include "PolyLineEntityItem.h"
const float PolyLineEntityItem::DEFAULT_LINE_WIDTH = 0.1f; const float PolyLineEntityItem::DEFAULT_LINE_WIDTH = 0.1f;
const int PolyLineEntityItem::MAX_POINTS_PER_LINE = 70; const int PolyLineEntityItem::MAX_POINTS_PER_LINE = 60;
EntityItemPointer PolyLineEntityItem::factory(const EntityItemID& entityID, const EntityItemProperties& properties) { EntityItemPointer PolyLineEntityItem::factory(const EntityItemID& entityID, const EntityItemProperties& properties) {
@ -31,6 +31,7 @@ EntityItemPointer PolyLineEntityItem::factory(const EntityItemID& entityID, cons
return entity; return entity;
} }
PolyLineEntityItem::PolyLineEntityItem(const EntityItemID& entityItemID) : EntityItem(entityItemID) { PolyLineEntityItem::PolyLineEntityItem(const EntityItemID& entityItemID) : EntityItem(entityItemID) {
_type = EntityTypes::PolyLine; _type = EntityTypes::PolyLine;
} }
@ -42,12 +43,15 @@ EntityItemProperties PolyLineEntityItem::getProperties(EntityPropertyFlags desir
properties._color = getXColor(); properties._color = getXColor();
properties._colorChanged = false; properties._colorChanged = false;
COPY_ENTITY_PROPERTY_TO_PROPERTIES(lineWidth, getLineWidth); COPY_ENTITY_PROPERTY_TO_PROPERTIES(lineWidth, getLineWidth);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(linePoints, getLinePoints); COPY_ENTITY_PROPERTY_TO_PROPERTIES(linePoints, getLinePoints);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(normals, getNormals); COPY_ENTITY_PROPERTY_TO_PROPERTIES(normals, getNormals);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(strokeColors, getStrokeColors);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(strokeWidths, getStrokeWidths); COPY_ENTITY_PROPERTY_TO_PROPERTIES(strokeWidths, getStrokeWidths);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(textures, getTextures); COPY_ENTITY_PROPERTY_TO_PROPERTIES(textures, getTextures);
COPY_ENTITY_PROPERTY_TO_PROPERTIES(isUVModeStretch, getIsUVModeStretch);
return properties; return properties;
} }
@ -60,8 +64,10 @@ bool PolyLineEntityItem::setProperties(const EntityItemProperties& properties) {
SET_ENTITY_PROPERTY_FROM_PROPERTIES(lineWidth, setLineWidth); SET_ENTITY_PROPERTY_FROM_PROPERTIES(lineWidth, setLineWidth);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(linePoints, setLinePoints); SET_ENTITY_PROPERTY_FROM_PROPERTIES(linePoints, setLinePoints);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(normals, setNormals); SET_ENTITY_PROPERTY_FROM_PROPERTIES(normals, setNormals);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(strokeColors, setStrokeColors);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(strokeWidths, setStrokeWidths); SET_ENTITY_PROPERTY_FROM_PROPERTIES(strokeWidths, setStrokeWidths);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(textures, setTextures); SET_ENTITY_PROPERTY_FROM_PROPERTIES(textures, setTextures);
SET_ENTITY_PROPERTY_FROM_PROPERTIES(isUVModeStretch, setIsUVModeStretch);
if (somethingChanged) { if (somethingChanged) {
bool wantDebug = false; bool wantDebug = false;
@ -108,6 +114,15 @@ bool PolyLineEntityItem::setNormals(const QVector<glm::vec3>& normals) {
return true; return true;
} }
bool PolyLineEntityItem::setStrokeColors(const QVector<glm::vec3>& strokeColors) {
withWriteLock([&] {
_strokeColors = strokeColors;
_strokeColorsChanged = true;
});
return true;
}
bool PolyLineEntityItem::setLinePoints(const QVector<glm::vec3>& points) { bool PolyLineEntityItem::setLinePoints(const QVector<glm::vec3>& points) {
if (points.size() > MAX_POINTS_PER_LINE) { if (points.size() > MAX_POINTS_PER_LINE) {
return false; return false;
@ -193,8 +208,10 @@ int PolyLineEntityItem::readEntitySubclassDataFromBuffer(const unsigned char* da
READ_ENTITY_PROPERTY(PROP_LINE_WIDTH, float, setLineWidth); READ_ENTITY_PROPERTY(PROP_LINE_WIDTH, float, setLineWidth);
READ_ENTITY_PROPERTY(PROP_LINE_POINTS, QVector<glm::vec3>, setLinePoints); READ_ENTITY_PROPERTY(PROP_LINE_POINTS, QVector<glm::vec3>, setLinePoints);
READ_ENTITY_PROPERTY(PROP_NORMALS, QVector<glm::vec3>, setNormals); READ_ENTITY_PROPERTY(PROP_NORMALS, QVector<glm::vec3>, setNormals);
READ_ENTITY_PROPERTY(PROP_STROKE_COLORS, QVector<glm::vec3>, setStrokeColors);
READ_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, QVector<float>, setStrokeWidths); READ_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, QVector<float>, setStrokeWidths);
READ_ENTITY_PROPERTY(PROP_TEXTURES, QString, setTextures); READ_ENTITY_PROPERTY(PROP_TEXTURES, QString, setTextures);
READ_ENTITY_PROPERTY(PROP_IS_UV_MODE_STRETCH, bool, setIsUVModeStretch);
return bytesRead; return bytesRead;
} }
@ -207,8 +224,10 @@ EntityPropertyFlags PolyLineEntityItem::getEntityProperties(EncodeBitstreamParam
requestedProperties += PROP_LINE_WIDTH; requestedProperties += PROP_LINE_WIDTH;
requestedProperties += PROP_LINE_POINTS; requestedProperties += PROP_LINE_POINTS;
requestedProperties += PROP_NORMALS; requestedProperties += PROP_NORMALS;
requestedProperties += PROP_STROKE_COLORS;
requestedProperties += PROP_STROKE_WIDTHS; requestedProperties += PROP_STROKE_WIDTHS;
requestedProperties += PROP_TEXTURES; requestedProperties += PROP_TEXTURES;
requestedProperties += PROP_IS_UV_MODE_STRETCH;
return requestedProperties; return requestedProperties;
} }
@ -227,8 +246,10 @@ void PolyLineEntityItem::appendSubclassData(OctreePacketData* packetData, Encode
APPEND_ENTITY_PROPERTY(PROP_LINE_WIDTH, getLineWidth()); APPEND_ENTITY_PROPERTY(PROP_LINE_WIDTH, getLineWidth());
APPEND_ENTITY_PROPERTY(PROP_LINE_POINTS, getLinePoints()); APPEND_ENTITY_PROPERTY(PROP_LINE_POINTS, getLinePoints());
APPEND_ENTITY_PROPERTY(PROP_NORMALS, getNormals()); APPEND_ENTITY_PROPERTY(PROP_NORMALS, getNormals());
APPEND_ENTITY_PROPERTY(PROP_STROKE_COLORS, getStrokeColors());
APPEND_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, getStrokeWidths()); APPEND_ENTITY_PROPERTY(PROP_STROKE_WIDTHS, getStrokeWidths());
APPEND_ENTITY_PROPERTY(PROP_TEXTURES, getTextures()); APPEND_ENTITY_PROPERTY(PROP_TEXTURES, getTextures());
APPEND_ENTITY_PROPERTY(PROP_IS_UV_MODE_STRETCH, getIsUVModeStretch());
} }
void PolyLineEntityItem::debugDump() const { void PolyLineEntityItem::debugDump() const {
@ -258,6 +279,14 @@ QVector<glm::vec3> PolyLineEntityItem::getNormals() const {
return result; return result;
} }
QVector<glm::vec3> PolyLineEntityItem::getStrokeColors() const {
QVector<glm::vec3> result;
withReadLock([&] {
result = _strokeColors;
});
return result;
}
QVector<float> PolyLineEntityItem::getStrokeWidths() const { QVector<float> PolyLineEntityItem::getStrokeWidths() const {
QVector<float> result; QVector<float> result;
withReadLock([&] { withReadLock([&] {

View file

@ -46,9 +46,11 @@ class PolyLineEntityItem : public EntityItem {
xColor getXColor() const { xColor color = { _color[RED_INDEX], _color[GREEN_INDEX], _color[BLUE_INDEX] }; return color; } xColor getXColor() const { xColor color = { _color[RED_INDEX], _color[GREEN_INDEX], _color[BLUE_INDEX] }; return color; }
void setColor(const rgbColor& value) { void setColor(const rgbColor& value) {
_strokeColorsChanged = true;
memcpy(_color, value, sizeof(_color)); memcpy(_color, value, sizeof(_color));
} }
void setColor(const xColor& value) { void setColor(const xColor& value) {
_strokeColorsChanged = true;
_color[RED_INDEX] = value.red; _color[RED_INDEX] = value.red;
_color[GREEN_INDEX] = value.green; _color[GREEN_INDEX] = value.green;
_color[BLUE_INDEX] = value.blue; _color[BLUE_INDEX] = value.blue;
@ -64,9 +66,15 @@ class PolyLineEntityItem : public EntityItem {
bool setNormals(const QVector<glm::vec3>& normals); bool setNormals(const QVector<glm::vec3>& normals);
QVector<glm::vec3> getNormals() const; QVector<glm::vec3> getNormals() const;
bool setStrokeColors(const QVector<glm::vec3>& strokeColors);
QVector<glm::vec3> getStrokeColors() const;
bool setStrokeWidths(const QVector<float>& strokeWidths); bool setStrokeWidths(const QVector<float>& strokeWidths);
QVector<float> getStrokeWidths() const; QVector<float> getStrokeWidths() const;
void setIsUVModeStretch(bool isUVModeStretch){ _isUVModeStretch = isUVModeStretch; }
bool getIsUVModeStretch() const{ return _isUVModeStretch; }
QString getTextures() const; QString getTextures() const;
void setTextures(const QString& textures); void setTextures(const QString& textures);
@ -76,10 +84,11 @@ class PolyLineEntityItem : public EntityItem {
bool pointsChanged() const { return _pointsChanged; } bool pointsChanged() const { return _pointsChanged; }
bool normalsChanged() const { return _normalsChanged; } bool normalsChanged() const { return _normalsChanged; }
bool strokeColorsChanged() const { return _strokeColorsChanged; }
bool strokeWidthsChanged() const { return _strokeWidthsChanged; } bool strokeWidthsChanged() const { return _strokeWidthsChanged; }
bool texturesChanged() const { return _texturesChangedFlag; } bool texturesChanged() const { return _texturesChangedFlag; }
void resetTexturesChanged() { _texturesChangedFlag = false; } void resetTexturesChanged() { _texturesChangedFlag = false; }
void resetPolyLineChanged() { _strokeWidthsChanged = _normalsChanged = _pointsChanged = false; } void resetPolyLineChanged() { _strokeColorsChanged = _strokeWidthsChanged = _normalsChanged = _pointsChanged = false; }
// never have a ray intersection pick a PolyLineEntityItem. // never have a ray intersection pick a PolyLineEntityItem.
@ -103,11 +112,14 @@ private:
float _lineWidth { DEFAULT_LINE_WIDTH }; float _lineWidth { DEFAULT_LINE_WIDTH };
bool _pointsChanged { true }; bool _pointsChanged { true };
bool _normalsChanged { true }; bool _normalsChanged { true };
bool _strokeColorsChanged { true };
bool _strokeWidthsChanged { true }; bool _strokeWidthsChanged { true };
QVector<glm::vec3> _points; QVector<glm::vec3> _points;
QVector<glm::vec3> _normals; QVector<glm::vec3> _normals;
QVector<glm::vec3> _strokeColors;
QVector<float> _strokeWidths; QVector<float> _strokeWidths;
QString _textures; QString _textures;
bool _isUVModeStretch;
bool _texturesChangedFlag { false }; bool _texturesChangedFlag { false };
mutable QReadWriteLock _quadReadWriteLock; mutable QReadWriteLock _quadReadWriteLock;
}; };

View file

@ -29,6 +29,7 @@ PacketVersion versionForPacketType(PacketType packetType) {
case PacketType::EntityAdd: case PacketType::EntityAdd:
case PacketType::EntityEdit: case PacketType::EntityEdit:
case PacketType::EntityData: case PacketType::EntityData:
return VERSION_ENTITIES_STROKE_COLOR_PROPERTY;
case PacketType::EntityPhysics: case PacketType::EntityPhysics:
return VERSION_ENTITIES_HAZE; return VERSION_ENTITIES_HAZE;
case PacketType::EntityQuery: case PacketType::EntityQuery:

View file

@ -269,6 +269,9 @@ const PacketVersion VERSION_ENTITIES_HAS_HIGHLIGHT_SCRIPTING_INTERFACE = 72;
const PacketVersion VERSION_ENTITIES_ANIMATION_ALLOW_TRANSLATION_PROPERTIES = 73; const PacketVersion VERSION_ENTITIES_ANIMATION_ALLOW_TRANSLATION_PROPERTIES = 73;
const PacketVersion VERSION_ENTITIES_HAS_CERTIFICATE_PROPERTIES = 74; const PacketVersion VERSION_ENTITIES_HAS_CERTIFICATE_PROPERTIES = 74;
const PacketVersion VERSION_ENTITIES_HAZE = 75; const PacketVersion VERSION_ENTITIES_HAZE = 75;
const PacketVersion VERSION_ENTITIES_UV_MODE_PROPERTY = 76;
const PacketVersion VERSION_ENTITIES_STROKE_COLOR_PROPERTY = 77;
enum class EntityQueryPacketVersion: PacketVersion { enum class EntityQueryPacketVersion: PacketVersion {
JSONFilter = 18, JSONFilter = 18,

View file

@ -33,6 +33,7 @@
/// Scriptable interface a Quaternion helper class object. Used exclusively in the JavaScript API /// Scriptable interface a Quaternion helper class object. Used exclusively in the JavaScript API
class Quat : public QObject, protected QScriptable { class Quat : public QObject, protected QScriptable {
Q_OBJECT Q_OBJECT
Q_PROPERTY(glm::quat IDENTITY READ IDENTITY CONSTANT)
public slots: public slots:
glm::quat multiply(const glm::quat& q1, const glm::quat& q2); glm::quat multiply(const glm::quat& q1, const glm::quat& q2);
@ -63,6 +64,10 @@ public slots:
bool equal(const glm::quat& q1, const glm::quat& q2); bool equal(const glm::quat& q1, const glm::quat& q2);
glm::quat cancelOutRollAndPitch(const glm::quat& q); glm::quat cancelOutRollAndPitch(const glm::quat& q);
glm::quat cancelOutRoll(const glm::quat& q); glm::quat cancelOutRoll(const glm::quat& q);
private:
const glm::quat& IDENTITY() const { return Quaternions::IDENTITY; }
}; };
#endif // hifi_Quat_h #endif // hifi_Quat_h

View file

@ -20,6 +20,7 @@
/// Scriptable interface for a UUID helper class object. Used exclusively in the JavaScript API /// Scriptable interface for a UUID helper class object. Used exclusively in the JavaScript API
class ScriptUUID : public QObject, protected QScriptable { class ScriptUUID : public QObject, protected QScriptable {
Q_OBJECT Q_OBJECT
Q_PROPERTY(QString NULL READ NULL_UUID CONSTANT) // String for use in scripts.
public slots: public slots:
QUuid fromString(const QString& string); QUuid fromString(const QString& string);
@ -28,6 +29,10 @@ public slots:
bool isEqual(const QUuid& idA, const QUuid& idB); bool isEqual(const QUuid& idA, const QUuid& idB);
bool isNull(const QUuid& id); bool isNull(const QUuid& id);
void print(const QString& label, const QUuid& id); void print(const QString& label, const QUuid& id);
private:
const QString NULL_UUID() { return NULL_ID; }
const QString NULL_ID { "{00000000-0000-0000-0000-000000000000}" };
}; };
#endif // hifi_ScriptUUID_h #endif // hifi_ScriptUUID_h

View file

@ -41,6 +41,7 @@
#include <gl/OffscreenGLCanvas.h> #include <gl/OffscreenGLCanvas.h>
#include <gl/GLHelpers.h> #include <gl/GLHelpers.h>
#include <gl/Context.h> #include <gl/Context.h>
#include <shared/ReadWriteLockable.h>
#include "types/FileTypeProfile.h" #include "types/FileTypeProfile.h"
#include "types/HFWebEngineProfile.h" #include "types/HFWebEngineProfile.h"
@ -52,6 +53,53 @@ Q_LOGGING_CATEGORY(trace_render_qml, "trace.render.qml")
Q_LOGGING_CATEGORY(trace_render_qml_gl, "trace.render.qml.gl") Q_LOGGING_CATEGORY(trace_render_qml_gl, "trace.render.qml.gl")
Q_LOGGING_CATEGORY(offscreenFocus, "hifi.offscreen.focus") Q_LOGGING_CATEGORY(offscreenFocus, "hifi.offscreen.focus")
class OffscreenQmlWhitelist : public Dependency, private ReadWriteLockable {
SINGLETON_DEPENDENCY
public:
void addWhitelistContextHandler(const std::initializer_list<QUrl>& urls, const QmlContextCallback& callback) {
withWriteLock([&] {
for (const auto& url : urls) {
_callbacks[url].push_back(callback);
}
});
}
QList<QmlContextCallback> getCallbacksForUrl(const QUrl& url) const {
return resultWithReadLock<QList<QmlContextCallback>>([&] {
QList<QmlContextCallback> result;
auto itr = _callbacks.find(url);
if (_callbacks.end() != itr) {
result = *itr;
}
return result;
});
}
private:
QHash<QUrl, QList<QmlContextCallback>> _callbacks;
};
QSharedPointer<OffscreenQmlWhitelist> getQmlWhitelist() {
static std::once_flag once;
std::call_once(once, [&] {
DependencyManager::set<OffscreenQmlWhitelist>();
});
return DependencyManager::get<OffscreenQmlWhitelist>();
}
void OffscreenQmlSurface::addWhitelistContextHandler(const std::initializer_list<QUrl>& urls, const QmlContextCallback& callback) {
getQmlWhitelist()->addWhitelistContextHandler(urls, callback);
}
QmlContextCallback OffscreenQmlSurface::DEFAULT_CONTEXT_CALLBACK = [](QQmlContext*, QObject*) {};
struct TextureSet { struct TextureSet {
// The number of surfaces with this size // The number of surfaces with this size
size_t count { 0 }; size_t count { 0 };
@ -640,18 +688,26 @@ void OffscreenQmlSurface::setBaseUrl(const QUrl& baseUrl) {
_qmlContext->setBaseUrl(baseUrl); _qmlContext->setBaseUrl(baseUrl);
} }
void OffscreenQmlSurface::load(const QUrl& qmlSource, bool createNewContext, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback) { void OffscreenQmlSurface::load(const QUrl& qmlSource, bool createNewContext, const QmlContextCallback& onQmlLoadedCallback) {
if (QThread::currentThread() != thread()) { if (QThread::currentThread() != thread()) {
qCWarning(uiLogging) << "Called load on a non-surface thread"; qCWarning(uiLogging) << "Called load on a non-surface thread";
} }
// Synchronous loading may take a while; restart the deadlock timer // Synchronous loading may take a while; restart the deadlock timer
QMetaObject::invokeMethod(qApp, "updateHeartbeat", Qt::DirectConnection); QMetaObject::invokeMethod(qApp, "updateHeartbeat", Qt::DirectConnection);
// Get any whitelist functionality
QList<QmlContextCallback> callbacks = getQmlWhitelist()->getCallbacksForUrl(qmlSource);
// If we have whitelisted content, we must load a new context
createNewContext |= !callbacks.empty();
callbacks.push_back(onQmlLoadedCallback);
QQmlContext* targetContext = _qmlContext; QQmlContext* targetContext = _qmlContext;
if (_rootItem && createNewContext) { if (_rootItem && createNewContext) {
targetContext = new QQmlContext(targetContext); targetContext = new QQmlContext(targetContext);
} }
// FIXME eliminate loading of relative file paths for QML
QUrl finalQmlSource = qmlSource; QUrl finalQmlSource = qmlSource;
if ((qmlSource.isRelative() && !qmlSource.isEmpty()) || qmlSource.scheme() == QLatin1String("file")) { if ((qmlSource.isRelative() && !qmlSource.isEmpty()) || qmlSource.scheme() == QLatin1String("file")) {
finalQmlSource = _qmlContext->resolvedUrl(qmlSource); finalQmlSource = _qmlContext->resolvedUrl(qmlSource);
@ -659,29 +715,32 @@ void OffscreenQmlSurface::load(const QUrl& qmlSource, bool createNewContext, std
auto qmlComponent = new QQmlComponent(_qmlContext->engine(), finalQmlSource, QQmlComponent::PreferSynchronous); auto qmlComponent = new QQmlComponent(_qmlContext->engine(), finalQmlSource, QQmlComponent::PreferSynchronous);
if (qmlComponent->isLoading()) { if (qmlComponent->isLoading()) {
connect(qmlComponent, &QQmlComponent::statusChanged, this, connect(qmlComponent, &QQmlComponent::statusChanged, this, [=](QQmlComponent::Status) {
[this, qmlComponent, targetContext, onQmlLoadedCallback](QQmlComponent::Status) { finishQmlLoad(qmlComponent, targetContext, callbacks);
finishQmlLoad(qmlComponent, targetContext, onQmlLoadedCallback);
}); });
return; return;
} }
finishQmlLoad(qmlComponent, targetContext, onQmlLoadedCallback); finishQmlLoad(qmlComponent, targetContext, callbacks);
} }
void OffscreenQmlSurface::loadInNewContext(const QUrl& qmlSource, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback) { void OffscreenQmlSurface::loadInNewContext(const QUrl& qmlSource, const QmlContextCallback& onQmlLoadedCallback) {
load(qmlSource, true, onQmlLoadedCallback); load(qmlSource, true, onQmlLoadedCallback);
} }
void OffscreenQmlSurface::load(const QUrl& qmlSource, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback) { void OffscreenQmlSurface::load(const QUrl& qmlSource, const QmlContextCallback& onQmlLoadedCallback) {
load(qmlSource, false, onQmlLoadedCallback); load(qmlSource, false, onQmlLoadedCallback);
} }
void OffscreenQmlSurface::load(const QString& qmlSourceFile, const QmlContextCallback& onQmlLoadedCallback) {
return load(QUrl(qmlSourceFile), onQmlLoadedCallback);
}
void OffscreenQmlSurface::clearCache() { void OffscreenQmlSurface::clearCache() {
_qmlContext->engine()->clearComponentCache(); _qmlContext->engine()->clearComponentCache();
} }
void OffscreenQmlSurface::finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext* qmlContext, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback) { void OffscreenQmlSurface::finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext* qmlContext, const QList<QmlContextCallback>& callbacks) {
disconnect(qmlComponent, &QQmlComponent::statusChanged, this, 0); disconnect(qmlComponent, &QQmlComponent::statusChanged, this, 0);
if (qmlComponent->isError()) { if (qmlComponent->isError()) {
for (const auto& error : qmlComponent->errors()) { for (const auto& error : qmlComponent->errors()) {
@ -716,7 +775,9 @@ void OffscreenQmlSurface::finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext
// Make sure we will call callback for this codepath // Make sure we will call callback for this codepath
// Call this before qmlComponent->completeCreate() otherwise ghost window appears // Call this before qmlComponent->completeCreate() otherwise ghost window appears
if (newItem && _rootItem) { if (newItem && _rootItem) {
onQmlLoadedCallback(qmlContext, newObject); for (const auto& callback : callbacks) {
callback(qmlContext, newObject);
}
} }
QObject* eventBridge = qmlContext->contextProperty("eventBridge").value<QObject*>(); QObject* eventBridge = qmlContext->contextProperty("eventBridge").value<QObject*>();
@ -751,8 +812,11 @@ void OffscreenQmlSurface::finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext
_rootItem = newItem; _rootItem = newItem;
_rootItem->setParentItem(_quickWindow->contentItem()); _rootItem->setParentItem(_quickWindow->contentItem());
_rootItem->setSize(_quickWindow->renderTargetSize()); _rootItem->setSize(_quickWindow->renderTargetSize());
// Call this callback after rootitem is set, otherwise VrMenu wont work // Call this callback after rootitem is set, otherwise VrMenu wont work
onQmlLoadedCallback(qmlContext, newObject); for (const auto& callback : callbacks) {
callback(qmlContext, newObject);
}
} }
void OffscreenQmlSurface::updateQuick() { void OffscreenQmlSurface::updateQuick() {
@ -1018,7 +1082,24 @@ void OffscreenQmlSurface::synthesizeKeyPress(QString key, QObject* targetOverrid
} }
} }
static void forEachKeyboard(QQuickItem* item, std::function<void(QQuickItem*)> function) { static void forEachKeyboard(QQuickItem* parent, std::function<void(QQuickItem*)> function) {
if (!function) {
return;
}
auto keyboards = parent->findChildren<QObject*>("keyboard");
for (auto keyboardObject : keyboards) {
auto keyboard = qobject_cast<QQuickItem*>(keyboardObject);
if (keyboard) {
function(keyboard);
}
}
}
static const int TEXTINPUT_PASSWORD = 2;
static QQuickItem* getTopmostParent(QQuickItem* item) {
QObject* itemObject = item; QObject* itemObject = item;
while (itemObject) { while (itemObject) {
if (itemObject->parent()) { if (itemObject->parent()) {
@ -1028,22 +1109,9 @@ static void forEachKeyboard(QQuickItem* item, std::function<void(QQuickItem*)> f
} }
} }
auto keyboards = itemObject->findChildren<QObject*>("keyboard"); return qobject_cast<QQuickItem*> (itemObject);
for (auto keyboardObject : keyboards) {
auto keyboard = qobject_cast<QQuickItem*>(keyboardObject);
if (keyboard == nullptr) {
continue;
}
if (function) {
function(keyboard);
}
}
} }
static const int TEXTINPUT_PASSWORD = 2;
void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool numeric) { void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool numeric) {
#if Q_OS_ANDROID #if Q_OS_ANDROID
return; return;
@ -1066,10 +1134,14 @@ void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool n
// we need to somehow pass 'isPasswordField' to visible keyboard so it will change its 'mirror text' to asterixes // we need to somehow pass 'isPasswordField' to visible keyboard so it will change its 'mirror text' to asterixes
// the issue in some cases there might be more than one keyboard in object tree and it is hard to understand which one is being used at the moment // the issue in some cases there might be more than one keyboard in object tree and it is hard to understand which one is being used at the moment
// unfortunately attempts to check for visibility failed becuase visibility is not updated yet. So... I don't see other way than just update properties for all the keyboards // unfortunately attempts to check for visibility failed becuase visibility is not updated yet. So... I don't see other way than just update properties for all the keyboards
forEachKeyboard(item, [&](QQuickItem* keyboard) {
keyboard->setProperty("mirroredText", QVariant::fromValue(QString(""))); auto topmostParent = getTopmostParent(item);
keyboard->setProperty("password", isPasswordField); if (topmostParent) {
}); forEachKeyboard(topmostParent, [&](QQuickItem* keyboard) {
keyboard->setProperty("mirroredText", QVariant::fromValue(QString("")));
keyboard->setProperty("password", isPasswordField);
});
}
// for future probably makes sense to consider one of the following: // for future probably makes sense to consider one of the following:
// 1. make keyboard a singleton, which will be dynamically re-parented before showing // 1. make keyboard a singleton, which will be dynamically re-parented before showing
@ -1081,6 +1153,11 @@ void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool n
numeric = numeric || QString(item->metaObject()->className()).left(7) == "SpinBox"; numeric = numeric || QString(item->metaObject()->className()).left(7) == "SpinBox";
if (item->property("keyboardRaised").isValid()) { if (item->property("keyboardRaised").isValid()) {
forEachKeyboard(item, [&](QQuickItem* keyboard) {
keyboard->setProperty("mirroredText", QVariant::fromValue(QString("")));
keyboard->setProperty("password", isPasswordField);
});
// FIXME - HMD only: Possibly set value of "keyboardEnabled" per isHMDMode() for use in WebView.qml. // FIXME - HMD only: Possibly set value of "keyboardEnabled" per isHMDMode() for use in WebView.qml.
if (item->property("punctuationMode").isValid()) { if (item->property("punctuationMode").isValid()) {
item->setProperty("punctuationMode", QVariant(numeric)); item->setProperty("punctuationMode", QVariant(numeric));

View file

@ -35,12 +35,18 @@ class QQuickItem;
// one copy in flight, and one copy being used by the receiver // one copy in flight, and one copy being used by the receiver
#define GPU_RESOURCE_BUFFER_SIZE 3 #define GPU_RESOURCE_BUFFER_SIZE 3
using QmlContextCallback = std::function<void(QQmlContext*, QObject*)>;
class OffscreenQmlSurface : public QObject { class OffscreenQmlSurface : public QObject {
Q_OBJECT Q_OBJECT
Q_PROPERTY(bool focusText READ isFocusText NOTIFY focusTextChanged) Q_PROPERTY(bool focusText READ isFocusText NOTIFY focusTextChanged)
public: public:
static void setSharedContext(QOpenGLContext* context); static void setSharedContext(QOpenGLContext* context);
static QmlContextCallback DEFAULT_CONTEXT_CALLBACK;
static void addWhitelistContextHandler(const std::initializer_list<QUrl>& urls, const QmlContextCallback& callback);
static void addWhitelistContextHandler(const QUrl& url, const QmlContextCallback& callback) { addWhitelistContextHandler({ { url } }, callback); };
OffscreenQmlSurface(); OffscreenQmlSurface();
virtual ~OffscreenQmlSurface(); virtual ~OffscreenQmlSurface();
@ -50,12 +56,10 @@ public:
void resize(const QSize& size, bool forceResize = false); void resize(const QSize& size, bool forceResize = false);
QSize size() const; QSize size() const;
Q_INVOKABLE void load(const QUrl& qmlSource, bool createNewContext, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback = [](QQmlContext*, QObject*) {}); Q_INVOKABLE void load(const QUrl& qmlSource, bool createNewContext, const QmlContextCallback& onQmlLoadedCallback = DEFAULT_CONTEXT_CALLBACK);
Q_INVOKABLE void loadInNewContext(const QUrl& qmlSource, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback = [](QQmlContext*, QObject*) {}); Q_INVOKABLE void loadInNewContext(const QUrl& qmlSource, const QmlContextCallback& onQmlLoadedCallback = DEFAULT_CONTEXT_CALLBACK);
Q_INVOKABLE void load(const QUrl& qmlSource, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback = [](QQmlContext*, QObject*) {}); Q_INVOKABLE void load(const QUrl& qmlSource, const QmlContextCallback& onQmlLoadedCallback = DEFAULT_CONTEXT_CALLBACK);
Q_INVOKABLE void load(const QString& qmlSourceFile, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback = [](QQmlContext*, QObject*) {}) { Q_INVOKABLE void load(const QString& qmlSourceFile, const QmlContextCallback& onQmlLoadedCallback = DEFAULT_CONTEXT_CALLBACK);
return load(QUrl(qmlSourceFile), onQmlLoadedCallback);
}
void clearCache(); void clearCache();
void setMaxFps(uint8_t maxFps) { _maxFps = maxFps; } void setMaxFps(uint8_t maxFps) { _maxFps = maxFps; }
// Optional values for event handling // Optional values for event handling
@ -120,7 +124,7 @@ protected:
private: private:
static QOpenGLContext* getSharedContext(); static QOpenGLContext* getSharedContext();
void finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext* qmlContext, std::function<void(QQmlContext*, QObject*)> onQmlLoadedCallback); void finishQmlLoad(QQmlComponent* qmlComponent, QQmlContext* qmlContext, const QList<QmlContextCallback>& callbacks);
QPointF mapWindowToUi(const QPointF& sourcePosition, QObject* sourceObject); QPointF mapWindowToUi(const QPointF& sourcePosition, QObject* sourceObject);
void setupFbo(); void setupFbo();
bool allowNewFrame(uint8_t fps); bool allowNewFrame(uint8_t fps);

View file

@ -32,7 +32,7 @@ var DEFAULT_SCRIPTS_COMBINED = [
"system/tablet-ui/tabletUI.js" "system/tablet-ui/tabletUI.js"
]; ];
var DEFAULT_SCRIPTS_SEPARATE = [ var DEFAULT_SCRIPTS_SEPARATE = [
"system/controllers/controllerScripts.js", "system/controllers/controllerScripts.js"
// "system/chat.js" // "system/chat.js"
]; ];

View file

@ -1,5 +1,3 @@
var AVATAR_SELF_ID = "{00000000-0000-0000-0000-000000000001}";
var debugSphereBaseProperties = { var debugSphereBaseProperties = {
type: "Sphere", type: "Sphere",
dimensions: { x: 0.2, y: 0.2, z: 0.2 }, dimensions: { x: 0.2, y: 0.2, z: 0.2 },

View file

@ -12,7 +12,6 @@
Script.include("libraries/utils.js"); Script.include("libraries/utils.js");
var NULL_UUID = "{00000000-0000-0000-0000-000000000000}";
var DEFAULT_WEARABLE_DATA = { var DEFAULT_WEARABLE_DATA = {
joints: {} joints: {}
}; };
@ -116,7 +115,7 @@ function AttachedEntitiesManager() {
var allowedJoints = getEntityCustomData('wearable', grabbedEntity, DEFAULT_WEARABLE_DATA).joints; var allowedJoints = getEntityCustomData('wearable', grabbedEntity, DEFAULT_WEARABLE_DATA).joints;
var props = Entities.getEntityProperties(grabbedEntity, ["position", "parentID", "parentJointIndex"]); var props = Entities.getEntityProperties(grabbedEntity, ["position", "parentID", "parentJointIndex"]);
if (props.parentID === NULL_UUID || props.parentID === MyAvatar.sessionUUID) { if (props.parentID === Uuid.NULL || props.parentID === MyAvatar.sessionUUID) {
var bestJointName = ""; var bestJointName = "";
var bestJointIndex = -1; var bestJointIndex = -1;
var bestJointDistance = 0; var bestJointDistance = 0;
@ -168,7 +167,7 @@ function AttachedEntitiesManager() {
if (updatePresets) { if (updatePresets) {
this.updateRelativeOffsets(newEntity); this.updateRelativeOffsets(newEntity);
} }
} else if (props.parentID != NULL_UUID) { } else if (props.parentID != Uuid.NULL) {
// drop the entity and set it to have no parent (not on the avatar), unless it's being equipped in a hand. // drop the entity and set it to have no parent (not on the avatar), unless it's being equipped in a hand.
if (props.parentID === MyAvatar.sessionUUID && if (props.parentID === MyAvatar.sessionUUID &&
(props.parentJointIndex == MyAvatar.getJointIndex("RightHand") || (props.parentJointIndex == MyAvatar.getJointIndex("RightHand") ||
@ -176,7 +175,7 @@ function AttachedEntitiesManager() {
// this is equipped on a hand -- don't clear the parent. // this is equipped on a hand -- don't clear the parent.
} else { } else {
var wearProps = Entities.getEntityProperties(grabbedEntity); var wearProps = Entities.getEntityProperties(grabbedEntity);
wearProps.parentID = NULL_UUID; wearProps.parentID = Uuid.NULL;
wearProps.parentJointIndex = -1; wearProps.parentJointIndex = -1;
delete wearProps.id; delete wearProps.id;
delete wearProps.created; delete wearProps.created;

View file

@ -30,7 +30,6 @@ var OVERLAY_DATA = {
}; };
var AVATAR_MOVE_FOR_ACTIVE_DISTANCE = 0.8; // meters -- no longer away if avatar moves this far while away var AVATAR_MOVE_FOR_ACTIVE_DISTANCE = 0.8; // meters -- no longer away if avatar moves this far while away
var AVATAR_SELF_ID = "{00000000-0000-0000-0000-000000000001}";
var CAMERA_MATRIX = -7; var CAMERA_MATRIX = -7;
var OVERLAY_DATA_HMD = { var OVERLAY_DATA_HMD = {
@ -44,7 +43,7 @@ var OVERLAY_DATA_HMD = {
scale: 2 * MyAvatar.sensorToWorldScale, scale: 2 * MyAvatar.sensorToWorldScale,
emissive: true, emissive: true,
drawInFront: true, drawInFront: true,
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: CAMERA_MATRIX parentJointIndex: CAMERA_MATRIX
}; };

View file

@ -25,10 +25,10 @@
// The bubble model itself // The bubble model itself
var bubbleOverlay = Overlays.addOverlay("model", { var bubbleOverlay = Overlays.addOverlay("model", {
url: Script.resolvePath("assets/models/Bubble-v14.fbx"), // If you'd like to change the model, modify this line (and the dimensions below) url: Script.resolvePath("assets/models/Bubble-v14.fbx"), // If you'd like to change the model, modify this line (and the dimensions below)
dimensions: { x: 1.0, y: 0.75, z: 1.0 }, dimensions: { x: MyAvatar.sensorToWorldScale, y: 0.75 * MyAvatar.sensorToWorldScale, z: MyAvatar.sensorToWorldScale },
position: { x: MyAvatar.position.x, y: -MyAvatar.scale * 2 + MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE, z: MyAvatar.position.z }, position: { x: MyAvatar.position.x, y: -MyAvatar.scale * 2 + MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE, z: MyAvatar.position.z },
rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})), rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})),
scale: { x: 2 * MyAvatar.sensorToWorldScale, y: MyAvatar.scale * 0.5 + 0.2 * MyAvatar.sensorToWorldScale, z: 2 * MyAvatar.sensorToWorldScale }, scale: { x: 2 , y: MyAvatar.scale * 0.5 + 0.5, z: 2 },
visible: false, visible: false,
ignoreRayIntersection: true ignoreRayIntersection: true
}); });
@ -62,6 +62,11 @@
} }
Overlays.editOverlay(bubbleOverlay, { Overlays.editOverlay(bubbleOverlay, {
dimensions: {
x: MyAvatar.sensorToWorldScale,
y: 0.75 * MyAvatar.sensorToWorldScale,
z: MyAvatar.sensorToWorldScale
},
position: { position: {
x: MyAvatar.position.x, x: MyAvatar.position.x,
y: -MyAvatar.scale * 2 + MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE, y: -MyAvatar.scale * 2 + MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE,
@ -69,9 +74,9 @@
}, },
rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})), rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})),
scale: { scale: {
x: 2 * MyAvatar.sensorToWorldScale, x: 2 ,
y: MyAvatar.scale * 0.5 + 0.2 * MyAvatar.sensorToWorldScale, y: MyAvatar.scale * 0.5 + 0.5 ,
z: 2 * MyAvatar.sensorToWorldScale z: 2
}, },
visible: true visible: true
}); });
@ -107,6 +112,11 @@
if (delay < BUBBLE_RAISE_ANIMATION_DURATION_MS) { if (delay < BUBBLE_RAISE_ANIMATION_DURATION_MS) {
Overlays.editOverlay(bubbleOverlay, { Overlays.editOverlay(bubbleOverlay, {
dimensions: {
x: MyAvatar.sensorToWorldScale,
y: 0.75 * MyAvatar.sensorToWorldScale,
z: MyAvatar.sensorToWorldScale
},
// Quickly raise the bubble from the ground up // Quickly raise the bubble from the ground up
position: { position: {
x: MyAvatar.position.x, x: MyAvatar.position.x,
@ -115,14 +125,19 @@
}, },
rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})), rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})),
scale: { scale: {
x: 2 * MyAvatar.sensorToWorldScale, x: 2 ,
y: ((1 - ((BUBBLE_RAISE_ANIMATION_DURATION_MS - delay) / BUBBLE_RAISE_ANIMATION_DURATION_MS)) * MyAvatar.scale * 0.5 + 0.2 * MyAvatar.sensorToWorldScale), y: ((1 - ((BUBBLE_RAISE_ANIMATION_DURATION_MS - delay) / BUBBLE_RAISE_ANIMATION_DURATION_MS)) * MyAvatar.scale * 0.5 + 0.5),
z: 2 * MyAvatar.sensorToWorldScale z: 2
} }
}); });
} else { } else {
// Keep the bubble in place for a couple seconds // Keep the bubble in place for a couple seconds
Overlays.editOverlay(bubbleOverlay, { Overlays.editOverlay(bubbleOverlay, {
dimensions: {
x: MyAvatar.sensorToWorldScale,
y: 0.75 * MyAvatar.sensorToWorldScale,
z: MyAvatar.sensorToWorldScale
},
position: { position: {
x: MyAvatar.position.x, x: MyAvatar.position.x,
y: MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE, y: MyAvatar.position.y + MyAvatar.scale * BUBBLE_HEIGHT_SCALE,
@ -130,9 +145,9 @@
}, },
rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})), rotation: Quat.multiply(MyAvatar.orientation, Quat.fromVec3Degrees({x: 0.0, y: 180.0, z: 0.0})),
scale: { scale: {
x: 2 * MyAvatar.sensorToWorldScale, x: 2,
y: MyAvatar.scale * 0.5 + 0.2 * MyAvatar.sensorToWorldScale, y: MyAvatar.scale * 0.5 + 0.5 ,
z: 2 * MyAvatar.sensorToWorldScale z: 2
} }
}); });
} }

View file

@ -27,7 +27,7 @@ Script.include("/~/system/libraries/controllerDispatcherUtils.js");
var BASIC_TIMER_INTERVAL_MS = 1000 / TARGET_UPDATE_HZ; var BASIC_TIMER_INTERVAL_MS = 1000 / TARGET_UPDATE_HZ;
var PROFILE = false; var PROFILE = false;
var DEBUG = true; var DEBUG = false;
if (typeof Test !== "undefined") { if (typeof Test !== "undefined") {
PROFILE = true; PROFILE = true;

View file

@ -9,8 +9,6 @@
/* globals createControllerDisplay:true deleteControllerDisplay:true */ /* globals createControllerDisplay:true deleteControllerDisplay:true */
var PARENT_ID = "{00000000-0000-0000-0000-000000000001}";
function clamp(value, min, max) { function clamp(value, min, max) {
if (value < min) { if (value < min) {
return min; return min;
@ -178,7 +176,7 @@ createControllerDisplay = function(config) {
dimensions: Vec3.multiply(sensorScaleFactor, controller.dimensions), dimensions: Vec3.multiply(sensorScaleFactor, controller.dimensions),
localRotation: controller.rotation, localRotation: controller.rotation,
localPosition: Vec3.multiply(sensorScaleFactor, position), localPosition: Vec3.multiply(sensorScaleFactor, position),
parentID: PARENT_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: controller.jointIndex, parentJointIndex: controller.jointIndex,
ignoreRayIntersection: true ignoreRayIntersection: true
}); });
@ -198,7 +196,7 @@ createControllerDisplay = function(config) {
url: part.modelURL, url: part.modelURL,
localPosition: partPosition, localPosition: partPosition,
localRotation: innerRotation, localRotation: innerRotation,
parentID: PARENT_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: controller.jointIndex, parentJointIndex: controller.jointIndex,
ignoreRayIntersection: true ignoreRayIntersection: true
}; };

View file

@ -6,8 +6,8 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, AVATAR_SELF_ID, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND,
getControllerJointIndex, NULL_UUID, enableDispatcherModule, disableDispatcherModule, getControllerJointIndex, enableDispatcherModule, disableDispatcherModule,
Messages, makeDispatcherModuleParameters, makeRunningValues, Settings, entityHasActions, Messages, makeDispatcherModuleParameters, makeRunningValues, Settings, entityHasActions,
Vec3, Overlays, flatten, Xform, getControllerWorldLocation, ensureDynamic, entityIsCloneable, Vec3, Overlays, flatten, Xform, getControllerWorldLocation, ensureDynamic, entityIsCloneable,
cloneEntity, DISPATCHER_PROPERTIES cloneEntity, DISPATCHER_PROPERTIES
@ -333,7 +333,7 @@ EquipHotspotBuddy.prototype.update = function(deltaTime, timestamp, controllerDa
var props = controllerData.nearbyEntityPropertiesByID[hotspot.entityID]; var props = controllerData.nearbyEntityPropertiesByID[hotspot.entityID];
var hasParent = true; var hasParent = true;
if (props.parentID === NULL_UUID) { if (props.parentID === Uuid.NULL) {
hasParent = false; hasParent = false;
} }
@ -491,7 +491,7 @@ EquipHotspotBuddy.prototype.update = function(deltaTime, timestamp, controllerDa
} }
var reparentProps = { var reparentProps = {
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: handJointIndex, parentJointIndex: handJointIndex,
localVelocity: {x: 0, y: 0, z: 0}, localVelocity: {x: 0, y: 0, z: 0},
localAngularVelocity: {x: 0, y: 0, z: 0}, localAngularVelocity: {x: 0, y: 0, z: 0},
@ -539,7 +539,7 @@ EquipHotspotBuddy.prototype.update = function(deltaTime, timestamp, controllerDa
this.endEquipEntity = function () { this.endEquipEntity = function () {
Entities.editEntity(this.targetEntityID, { Entities.editEntity(this.targetEntityID, {
parentID: NULL_UUID, parentID: Uuid.NULL,
parentJointIndex: -1 parentJointIndex: -1
}); });

View file

@ -8,11 +8,11 @@
/* jslint bitwise: true */ /* jslint bitwise: true */
/* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Mat4, MyAvatar, Vec3, Camera, Quat, /* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Mat4, MyAvatar, Vec3, Camera, Quat,
getGrabPointSphereOffset, getEnabledModuleByName, makeRunningValues, Entities, NULL_UUID, getGrabPointSphereOffset, getEnabledModuleByName, makeRunningValues, Entities,
enableDispatcherModule, disableDispatcherModule, entityIsDistanceGrabbable, enableDispatcherModule, disableDispatcherModule, entityIsDistanceGrabbable, entityIsGrabbable,
makeDispatcherModuleParameters, MSECS_PER_SEC, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, makeDispatcherModuleParameters, MSECS_PER_SEC, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION,
PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD,
AVATAR_SELF_ID, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_OFF_VALUE, TRIGGER_ON_VALUE, ZERO_VEC, ensureDynamic, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_OFF_VALUE, TRIGGER_ON_VALUE, ZERO_VEC, ensureDynamic,
getControllerWorldLocation, projectOntoEntityXYPlane, ContextOverlay, HMD, Reticle, Overlays, isPointingAtUI getControllerWorldLocation, projectOntoEntityXYPlane, ContextOverlay, HMD, Reticle, Overlays, isPointingAtUI
*/ */
@ -23,6 +23,8 @@ Script.include("/~/system/libraries/controllers.js");
(function() { (function() {
var PICK_WITH_HAND_RAY = true; var PICK_WITH_HAND_RAY = true;
var SEARCH_SPHERE_SIZE = 0.0132;
var dim = {x: SEARCH_SPHERE_SIZE, y: SEARCH_SPHERE_SIZE, z: SEARCH_SPHERE_SIZE};
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -33,10 +35,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -54,10 +57,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -75,7 +79,7 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -135,10 +139,6 @@ Script.include("/~/system/libraries/controllers.js");
100); 100);
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var SEARCH_SPHERE_SIZE = 0.011;
var MIN_SPHERE_SIZE = 0.0005;
var radius = Math.max(1.2 * SEARCH_SPHERE_SIZE * this.intersectionDistance, MIN_SPHERE_SIZE) * MyAvatar.sensorToWorldScale;
var dim = {x: radius, y: radius, z: radius};
var mode = "hold"; var mode = "hold";
if (!this.distanceHolding && !this.distanceRotating) { if (!this.distanceHolding && !this.distanceRotating) {
if (controllerData.triggerClicks[this.hand]) { if (controllerData.triggerClicks[this.hand]) {
@ -150,16 +150,10 @@ Script.include("/~/system/libraries/controllers.js");
var laserPointerID = PICK_WITH_HAND_RAY ? this.laserPointer : this.headLaserPointer; var laserPointerID = PICK_WITH_HAND_RAY ? this.laserPointer : this.headLaserPointer;
if (mode === "full") { if (mode === "full") {
var fullEndToEdit = PICK_WITH_HAND_RAY ? this.fullEnd : fullEnd;
fullEndToEdit.dimensions = dim;
LaserPointers.editRenderState(laserPointerID, mode, { path: fullPath, end: fullEndToEdit });
this.contextOverlayTimer = false; this.contextOverlayTimer = false;
this.destroyContextOverlay(); this.destroyContextOverlay();
} else if (mode === "half") {
var halfEndToEdit = PICK_WITH_HAND_RAY ? this.halfEnd : halfEnd;
halfEndToEdit.dimensions = dim;
LaserPointers.editRenderState(laserPointerID, mode, {path: halfPath, end: halfEndToEdit});
} }
LaserPointers.enableLaserPointer(laserPointerID); LaserPointers.enableLaserPointer(laserPointerID);
LaserPointers.setRenderState(laserPointerID, mode); LaserPointers.setRenderState(laserPointerID, mode);
if (this.distanceHolding || this.distanceRotating) { if (this.distanceHolding || this.distanceRotating) {
@ -238,7 +232,7 @@ Script.include("/~/system/libraries/controllers.js");
tag: "far-grab-" + MyAvatar.sessionUUID, tag: "far-grab-" + MyAvatar.sessionUUID,
ttl: ACTION_TTL ttl: ACTION_TTL
}); });
if (this.actionID === NULL_UUID) { if (this.actionID === Uuid.NULL) {
this.actionID = null; this.actionID = null;
} }
@ -577,8 +571,6 @@ Script.include("/~/system/libraries/controllers.js");
LaserPointers.removeLaserPointer(this.laserPointer); LaserPointers.removeLaserPointer(this.laserPointer);
}; };
this.halfEnd = halfEnd;
this.fullEnd = fullEnd;
this.laserPointer = LaserPointers.createLaserPointer({ this.laserPointer = LaserPointers.createLaserPointer({
joint: (this.hand === RIGHT_HAND) ? "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND", joint: (this.hand === RIGHT_HAND) ? "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND",
filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS, filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS,
@ -586,6 +578,7 @@ Script.include("/~/system/libraries/controllers.js");
posOffset: getGrabPointSphereOffset(this.handToController(), true), posOffset: getGrabPointSphereOffset(this.handToController(), true),
renderStates: renderStates, renderStates: renderStates,
faceAvatar: true, faceAvatar: true,
distanceScaleEnd: true,
defaultRenderStates: defaultRenderStates defaultRenderStates: defaultRenderStates
}); });
} }

View file

@ -9,13 +9,15 @@
/* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, MyAvatar, getGrabPointSphereOffset, /* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, MyAvatar, getGrabPointSphereOffset,
makeRunningValues, Entities, enableDispatcherModule, disableDispatcherModule, makeDispatcherModuleParameters, makeRunningValues, Entities, enableDispatcherModule, disableDispatcherModule, makeDispatcherModuleParameters,
PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD,
AVATAR_SELF_ID, DEFAULT_SEARCH_SPHERE_DISTANCE, getGrabbableData DEFAULT_SEARCH_SPHERE_DISTANCE, getGrabbableData
*/ */
Script.include("/~/system/libraries/controllerDispatcherUtils.js"); Script.include("/~/system/libraries/controllerDispatcherUtils.js");
Script.include("/~/system/libraries/controllers.js"); Script.include("/~/system/libraries/controllers.js");
(function() { (function() {
var SEARCH_SPHERE_SIZE = 0.0132;
var dim = {x: SEARCH_SPHERE_SIZE, y: SEARCH_SPHERE_SIZE, z: SEARCH_SPHERE_SIZE};
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -26,10 +28,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -47,10 +50,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -68,7 +72,7 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -107,10 +111,6 @@ Script.include("/~/system/libraries/controllers.js");
}; };
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var SEARCH_SPHERE_SIZE = 0.011;
var MIN_SPHERE_SIZE = 0.0005;
var radius = Math.max(1.2 * SEARCH_SPHERE_SIZE * this.intersectionDistance, MIN_SPHERE_SIZE);
var dim = {x: radius, y: radius, z: radius};
var mode = "none"; var mode = "none";
if (controllerData.triggerClicks[this.hand]) { if (controllerData.triggerClicks[this.hand]) {
mode = "full"; mode = "full";
@ -118,18 +118,8 @@ Script.include("/~/system/libraries/controllers.js");
mode = "half"; mode = "half";
} }
var laserPointerID = this.laserPointer; LaserPointers.enableLaserPointer(this.laserPointer);
if (mode === "full") { LaserPointers.setRenderState(this.laserPointer, mode);
var fullEndToEdit = this.fullEnd;
fullEndToEdit.dimensions = dim;
LaserPointers.editRenderState(laserPointerID, mode, {path: fullPath, end: fullEndToEdit});
} else if (mode === "half") {
var halfEndToEdit = this.halfEnd;
halfEndToEdit.dimensions = dim;
LaserPointers.editRenderState(laserPointerID, mode, {path: halfPath, end: halfEndToEdit});
}
LaserPointers.enableLaserPointer(laserPointerID);
LaserPointers.setRenderState(laserPointerID, mode);
}; };
this.laserPointerOff = function() { this.laserPointerOff = function() {
@ -192,8 +182,6 @@ Script.include("/~/system/libraries/controllers.js");
return makeRunningValues(true, [this.targetEntityID], []); return makeRunningValues(true, [this.targetEntityID], []);
}; };
this.halfEnd = halfEnd;
this.fullEnd = fullEnd;
this.laserPointer = LaserPointers.createLaserPointer({ this.laserPointer = LaserPointers.createLaserPointer({
joint: (this.hand === RIGHT_HAND) ? "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND", joint: (this.hand === RIGHT_HAND) ? "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND",
filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS, filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS,
@ -201,6 +189,7 @@ Script.include("/~/system/libraries/controllers.js");
posOffset: getGrabPointSphereOffset(this.handToController(), true), posOffset: getGrabPointSphereOffset(this.handToController(), true),
renderStates: renderStates, renderStates: renderStates,
faceAvatar: true, faceAvatar: true,
distanceScaleEnd: true,
defaultRenderStates: defaultRenderStates defaultRenderStates: defaultRenderStates
}); });

View file

@ -11,17 +11,19 @@
// //
/* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Mat4, MyAvatar, Vec3, Camera, Quat, /* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Mat4, MyAvatar, Vec3, Camera, Quat,
getGrabPointSphereOffset, getEnabledModuleByName, makeRunningValues, Entities, NULL_UUID, getGrabPointSphereOffset, getEnabledModuleByName, makeRunningValues, Entities,
enableDispatcherModule, disableDispatcherModule, entityIsDistanceGrabbable, enableDispatcherModule, disableDispatcherModule, entityIsDistanceGrabbable,
makeDispatcherModuleParameters, MSECS_PER_SEC, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, makeDispatcherModuleParameters, MSECS_PER_SEC, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION,
PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD,
AVATAR_SELF_ID, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_OFF_VALUE, TRIGGER_ON_VALUE, ZERO_VEC, ensureDynamic, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_OFF_VALUE, TRIGGER_ON_VALUE, ZERO_VEC, ensureDynamic,
getControllerWorldLocation, projectOntoEntityXYPlane, ContextOverlay, HMD, Reticle, Overlays, isPointingAtUI getControllerWorldLocation, projectOntoEntityXYPlane, ContextOverlay, HMD, Reticle, Overlays, isPointingAtUI
*/ */
(function() { (function() {
Script.include("/~/system/libraries/controllers.js"); Script.include("/~/system/libraries/controllers.js");
var ControllerDispatcherUtils = Script.require("/~/system/libraries/controllerDispatcherUtils.js"); var ControllerDispatcherUtils = Script.require("/~/system/libraries/controllerDispatcherUtils.js");
var END_RADIUS = 0.005;
var dim = { x: END_RADIUS, y: END_RADIUS, z: END_RADIUS };
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -32,10 +34,11 @@
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawHUDLayer: true, drawHUDLayer: true,
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -53,10 +56,11 @@
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawHUDLayer: true, drawHUDLayer: true,
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -74,7 +78,7 @@
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawHUDLayer: true, drawHUDLayer: true,
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -126,17 +130,6 @@
}; };
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var RADIUS = 0.005;
var dim = { x: RADIUS, y: RADIUS, z: RADIUS };
if (this.mode === "full") {
this.fullEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: fullPath, end: this.fullEnd});
} else if (this.mode === "half") {
this.halfEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: halfPath, end: this.halfEnd});
}
LaserPointers.enableLaserPointer(this.laserPointer); LaserPointers.enableLaserPointer(this.laserPointer);
LaserPointers.setRenderState(this.laserPointer, this.mode); LaserPointers.setRenderState(this.laserPointer, this.mode);
}; };
@ -212,8 +205,6 @@
LaserPointers.removeLaserPointer(this.laserPointer); LaserPointers.removeLaserPointer(this.laserPointer);
}; };
this.halfEnd = halfEnd;
this.fullEnd = fullEnd;
this.laserPointer = LaserPointers.createLaserPointer({ this.laserPointer = LaserPointers.createLaserPointer({
joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND", joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND",
filter: RayPick.PICK_HUD, filter: RayPick.PICK_HUD,

View file

@ -8,7 +8,7 @@
/* jslint bitwise: true */ /* jslint bitwise: true */
/* global Script, Controller, RIGHT_HAND, LEFT_HAND, enableDispatcherModule, disableDispatcherModule, makeRunningValues, /* global Script, Controller, RIGHT_HAND, LEFT_HAND, enableDispatcherModule, disableDispatcherModule, makeRunningValues,
Messages, makeDispatcherModuleParameters, AVATAR_SELF_ID, HMD, getGrabPointSphereOffset, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, Messages, makeDispatcherModuleParameters, HMD, getGrabPointSphereOffset, COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE,
getEnabledModuleByName, PICK_MAX_DISTANCE, isInEditMode, LaserPointers, RayPick getEnabledModuleByName, PICK_MAX_DISTANCE, isInEditMode, LaserPointers, RayPick
*/ */
@ -18,6 +18,8 @@ Script.include("/~/system/libraries/controllers.js");
Script.include("/~/system/libraries/utils.js"); Script.include("/~/system/libraries/utils.js");
(function () { (function () {
var END_RADIUS = 0.005;
var dim = { x: END_RADIUS, y: END_RADIUS, z: END_RADIUS };
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -28,10 +30,11 @@ Script.include("/~/system/libraries/utils.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -49,10 +52,11 @@ Script.include("/~/system/libraries/utils.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -70,7 +74,7 @@ Script.include("/~/system/libraries/utils.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -121,17 +125,6 @@ Script.include("/~/system/libraries/utils.js");
}; };
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var RADIUS = 0.005;
var dim = { x: RADIUS, y: RADIUS, z: RADIUS };
if (this.mode === "full") {
this.fullEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: fullPath, end: this.fullEnd});
} else if (this.mode === "half") {
this.halfEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: halfPath, end: this.halfEnd});
}
LaserPointers.enableLaserPointer(this.laserPointer); LaserPointers.enableLaserPointer(this.laserPointer);
LaserPointers.setRenderState(this.laserPointer, this.mode); LaserPointers.setRenderState(this.laserPointer, this.mode);
}; };
@ -230,10 +223,6 @@ Script.include("/~/system/libraries/utils.js");
LaserPointers.removeLaserPointer(this.laserPointer); LaserPointers.removeLaserPointer(this.laserPointer);
}; };
this.halfEnd = halfEnd;
this.fullEnd = fullEnd;
this.laserPointer = LaserPointers.createLaserPointer({ this.laserPointer = LaserPointers.createLaserPointer({
joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND", joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND",
filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS, filter: RayPick.PICK_ENTITIES | RayPick.PICK_OVERLAYS,

View file

@ -6,7 +6,7 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND,
getControllerJointIndex, getGrabbableData, NULL_UUID, enableDispatcherModule, disableDispatcherModule, getControllerJointIndex, getGrabbableData, enableDispatcherModule, disableDispatcherModule,
propsArePhysical, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, entityIsGrabbable, propsArePhysical, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, entityIsGrabbable,
Quat, Vec3, MSECS_PER_SEC, getControllerWorldLocation, makeDispatcherModuleParameters, makeRunningValues, Quat, Vec3, MSECS_PER_SEC, getControllerWorldLocation, makeDispatcherModuleParameters, makeRunningValues,
TRIGGER_OFF_VALUE, NEAR_GRAB_RADIUS, findGroupParent, entityIsCloneable, propsAreCloneDynamic, cloneEntity, TRIGGER_OFF_VALUE, NEAR_GRAB_RADIUS, findGroupParent, entityIsCloneable, propsAreCloneDynamic, cloneEntity,
@ -101,7 +101,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
kinematicSetVelocity: true, kinematicSetVelocity: true,
ignoreIK: this.ignoreIK ignoreIK: this.ignoreIK
}); });
if (this.actionID === NULL_UUID) { if (this.actionID === Uuid.NULL) {
this.actionID = null; this.actionID = null;
return; return;
} }
@ -189,7 +189,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
if (targetProps) { if (targetProps) {
if ((!propsArePhysical(targetProps) && !propsAreCloneDynamic(targetProps)) || if ((!propsArePhysical(targetProps) && !propsAreCloneDynamic(targetProps)) ||
targetProps.parentID != NULL_UUID) { targetProps.parentID !== Uuid.NULL) {
return makeRunningValues(false, [], []); // let nearParentGrabEntity handle it return makeRunningValues(false, [], []); // let nearParentGrabEntity handle it
} else { } else {
this.targetEntityID = targetProps.id; this.targetEntityID = targetProps.id;

View file

@ -6,7 +6,7 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, AVATAR_SELF_ID, getControllerJointIndex, NULL_UUID, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, getControllerJointIndex,
enableDispatcherModule, disableDispatcherModule, propsArePhysical, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, enableDispatcherModule, disableDispatcherModule, propsArePhysical, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION,
TRIGGER_OFF_VALUE, makeDispatcherModuleParameters, entityIsGrabbable, makeRunningValues, NEAR_GRAB_RADIUS, TRIGGER_OFF_VALUE, makeDispatcherModuleParameters, entityIsGrabbable, makeRunningValues, NEAR_GRAB_RADIUS,
findGroupParent, Vec3, cloneEntity, entityIsCloneable, propsAreCloneDynamic, HAPTIC_PULSE_STRENGTH, findGroupParent, Vec3, cloneEntity, entityIsCloneable, propsAreCloneDynamic, HAPTIC_PULSE_STRENGTH,
@ -50,7 +50,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
return false; return false;
} }
if (props.parentID !== MyAvatar.sessionUUID && props.parentID !== AVATAR_SELF_ID) { if (props.parentID !== MyAvatar.sessionUUID && props.parentID !== MyAvatar.SELF_ID) {
return false; return false;
} }
@ -90,7 +90,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
Entities.callEntityMethod(targetProps.id, "startNearGrab", args); Entities.callEntityMethod(targetProps.id, "startNearGrab", args);
var reparentProps = { var reparentProps = {
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: handJointIndex, parentJointIndex: handJointIndex,
localVelocity: {x: 0, y: 0, z: 0}, localVelocity: {x: 0, y: 0, z: 0},
localAngularVelocity: {x: 0, y: 0, z: 0} localAngularVelocity: {x: 0, y: 0, z: 0}
@ -120,7 +120,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
this.hapticTargetID = null; this.hapticTargetID = null;
var props = controllerData.nearbyEntityPropertiesByID[this.targetEntityID]; var props = controllerData.nearbyEntityPropertiesByID[this.targetEntityID];
if (this.thisHandIsParent(props)) { if (this.thisHandIsParent(props)) {
if (this.previousParentID[this.targetEntityID] === NULL_UUID || this.previousParentID === undefined) { if (this.previousParentID[this.targetEntityID] === Uuid.NULL || this.previousParentID === undefined) {
Entities.editEntity(this.targetEntityID, { Entities.editEntity(this.targetEntityID, {
parentID: this.previousParentID[this.targetEntityID], parentID: this.previousParentID[this.targetEntityID],
parentJointIndex: this.previousParentJointIndex[this.targetEntityID] parentJointIndex: this.previousParentJointIndex[this.targetEntityID]
@ -152,7 +152,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
var now = Date.now(); var now = Date.now();
if (now - this.lastUnequipCheckTime > MSECS_PER_SEC * TEAR_AWAY_CHECK_TIME) { if (now - this.lastUnequipCheckTime > MSECS_PER_SEC * TEAR_AWAY_CHECK_TIME) {
this.lastUnequipCheckTime = now; this.lastUnequipCheckTime = now;
if (props.parentID == AVATAR_SELF_ID) { if (props.parentID === MyAvatar.SELF_ID) {
var sensorScaleFactor = MyAvatar.sensorToWorldScale; var sensorScaleFactor = MyAvatar.sensorToWorldScale;
var handPosition = controllerData.controllerLocations[this.hand].position; var handPosition = controllerData.controllerLocations[this.hand].position;
var dist = distanceBetweenPointAndEntityBoundingBox(handPosition, props); var dist = distanceBetweenPointAndEntityBoundingBox(handPosition, props);
@ -198,7 +198,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
var UNHOOK_LOOP_DETECT_MS = 200; var UNHOOK_LOOP_DETECT_MS = 200;
if (_this.previouslyUnhooked[childID]) { if (_this.previouslyUnhooked[childID]) {
if (now - _this.previouslyUnhooked[childID] < UNHOOK_LOOP_DETECT_MS) { if (now - _this.previouslyUnhooked[childID] < UNHOOK_LOOP_DETECT_MS) {
previousParentID = NULL_UUID; previousParentID = Uuid.NULL;
previousParentJointIndex = -1; previousParentJointIndex = -1;
} }
} }
@ -209,7 +209,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
parentJointIndex: previousParentJointIndex parentJointIndex: previousParentJointIndex
}); });
} else { } else {
Entities.editEntity(childID, { parentID: NULL_UUID }); Entities.editEntity(childID, { parentID: Uuid.NULL });
} }
}); });
} }
@ -258,7 +258,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
if (targetProps) { if (targetProps) {
if ((propsArePhysical(targetProps) || propsAreCloneDynamic(targetProps)) && if ((propsArePhysical(targetProps) || propsAreCloneDynamic(targetProps)) &&
targetProps.parentID == NULL_UUID) { targetProps.parentID === Uuid.NULL) {
return makeRunningValues(false, [], []); // let nearActionGrabEntity handle it return makeRunningValues(false, [], []); // let nearActionGrabEntity handle it
} else { } else {
this.targetEntityID = targetProps.id; this.targetEntityID = targetProps.id;
@ -273,7 +273,7 @@ Script.include("/~/system/libraries/cloneEntityUtils.js");
this.run = function (controllerData, deltaTime) { this.run = function (controllerData, deltaTime) {
if (this.grabbing) { if (this.grabbing) {
if (controllerData.triggerClicks[this.hand] < TRIGGER_OFF_VALUE && if (controllerData.triggerClicks[this.hand] < TRIGGER_OFF_VALUE &&
controllerData.secondaryValues[this.hand] < TRIGGER_OFF_VALUE) { controllerData.secondaryValues[this.hand] < TRIGGER_OFF_VALUE) {
this.endNearParentingGrabEntity(controllerData); this.endNearParentingGrabEntity(controllerData);
return makeRunningValues(false, [], []); return makeRunningValues(false, [], []);
} }

View file

@ -6,7 +6,7 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, AVATAR_SELF_ID, getControllerJointIndex, NULL_UUID, /* global Script, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, getControllerJointIndex,
enableDispatcherModule, disableDispatcherModule, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION, enableDispatcherModule, disableDispatcherModule, Messages, HAPTIC_PULSE_STRENGTH, HAPTIC_PULSE_DURATION,
makeDispatcherModuleParameters, Overlays, makeRunningValues, Vec3, resizeTablet, getTabletWidthFromSettings, makeDispatcherModuleParameters, Overlays, makeRunningValues, Vec3, resizeTablet, getTabletWidthFromSettings,
NEAR_GRAB_RADIUS NEAR_GRAB_RADIUS
@ -48,7 +48,7 @@ Script.include("/~/system/libraries/utils.js");
}; };
this.thisHandIsParent = function(props) { this.thisHandIsParent = function(props) {
if (props.parentID !== MyAvatar.sessionUUID && props.parentID !== AVATAR_SELF_ID) { if (props.parentID !== MyAvatar.sessionUUID && props.parentID !== MyAvatar.SELF_ID) {
return false; return false;
} }
@ -94,7 +94,7 @@ Script.include("/~/system/libraries/utils.js");
var grabbedProperties = this.getGrabbedProperties(); var grabbedProperties = this.getGrabbedProperties();
var reparentProps = { var reparentProps = {
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: handJointIndex, parentJointIndex: handJointIndex,
velocity: {x: 0, y: 0, z: 0}, velocity: {x: 0, y: 0, z: 0},
angularVelocity: {x: 0, y: 0, z: 0} angularVelocity: {x: 0, y: 0, z: 0}
@ -130,9 +130,9 @@ Script.include("/~/system/libraries/utils.js");
this.endNearParentingGrabOverlay = function () { this.endNearParentingGrabOverlay = function () {
var previousParentID = this.previousParentID[this.grabbedThingID]; var previousParentID = this.previousParentID[this.grabbedThingID];
if ((previousParentID === NULL_UUID || previousParentID === null) && !this.robbed) { if ((previousParentID === Uuid.NULL || previousParentID === null) && !this.robbed) {
Overlays.editOverlay(this.grabbedThingID, { Overlays.editOverlay(this.grabbedThingID, {
parentID: NULL_UUID, parentID: Uuid.NULL,
parentJointIndex: -1 parentJointIndex: -1
}); });
} else if (!this.robbed){ } else if (!this.robbed){

View file

@ -5,8 +5,8 @@
// Distributed under the Apache License, Version 2.0. // Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, Controller, RIGHT_HAND, LEFT_HAND, NULL_UUID, enableDispatcherModule, disableDispatcherModule, /* global Script, Entities, Controller, RIGHT_HAND, LEFT_HAND, enableDispatcherModule, disableDispatcherModule,
makeRunningValues, Messages, Quat, Vec3, makeDispatcherModuleParameters, Overlays, ZERO_VEC, AVATAR_SELF_ID, HMD, makeRunningValues, Messages, Quat, Vec3, makeDispatcherModuleParameters, Overlays, ZERO_VEC, HMD,
INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, getGrabPointSphereOffset, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, getGrabPointSphereOffset, COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE,
TRIGGER_OFF_VALUE, getEnabledModuleByName, PICK_MAX_DISTANCE, LaserPointers, RayPick, ContextOverlay TRIGGER_OFF_VALUE, getEnabledModuleByName, PICK_MAX_DISTANCE, LaserPointers, RayPick, ContextOverlay
@ -17,6 +17,8 @@ Script.include("/~/system/libraries/controllers.js");
(function() { (function() {
var TouchEventUtils = Script.require("/~/system/libraries/touchEventUtils.js"); var TouchEventUtils = Script.require("/~/system/libraries/touchEventUtils.js");
var END_RADIUS = 0.005;
var dim = { x: END_RADIUS, y: END_RADIUS, z: END_RADIUS };
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -27,10 +29,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -48,10 +51,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -69,7 +73,7 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -171,17 +175,6 @@ Script.include("/~/system/libraries/controllers.js");
}; };
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var RADIUS = 0.005;
var dim = { x: RADIUS, y: RADIUS, z: RADIUS };
if (this.mode === "full") {
this.fullEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: fullPath, end: this.fullEnd});
} else if (this.mode === "half") {
this.halfEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: halfPath, end: this.halfEnd});
}
LaserPointers.enableLaserPointer(this.laserPointer); LaserPointers.enableLaserPointer(this.laserPointer);
LaserPointers.setRenderState(this.laserPointer, this.mode); LaserPointers.setRenderState(this.laserPointer, this.mode);
}; };
@ -235,7 +228,7 @@ Script.include("/~/system/libraries/controllers.js");
var POINTER_PRESS_TO_MOVE_DELAY = 0.33; // seconds var POINTER_PRESS_TO_MOVE_DELAY = 0.33; // seconds
if (this.deadspotExpired || this.touchingEnterTimer > POINTER_PRESS_TO_MOVE_DELAY || if (this.deadspotExpired || this.touchingEnterTimer > POINTER_PRESS_TO_MOVE_DELAY ||
distance2D(this.laserTarget.position2D, distance2D(this.laserTarget.position2D,
this.pressEnterLaserTarget.position2D) > this.deadspotRadius) { this.pressEnterLaserTarget.position2D) > this.deadspotRadius) {
TouchEventUtils.sendTouchMoveEventToTouchTarget(this.hand, this.laserTarget); TouchEventUtils.sendTouchMoveEventToTouchTarget(this.hand, this.laserTarget);
this.deadspotExpired = true; this.deadspotExpired = true;
} }
@ -366,8 +359,6 @@ Script.include("/~/system/libraries/controllers.js");
LaserPointers.removeLaserPointer(this.laserPointer); LaserPointers.removeLaserPointer(this.laserPointer);
}; };
this.halfEnd = halfEnd;
this.fullEnd = fullEnd;
this.laserPointer = LaserPointers.createLaserPointer({ this.laserPointer = LaserPointers.createLaserPointer({
joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND", joint: (this.hand === RIGHT_HAND) ? "_CONTROLLER_RIGHTHAND" : "_CONTROLLER_LEFTHAND",
filter: RayPick.PICK_OVERLAYS, filter: RayPick.PICK_OVERLAYS,

View file

@ -6,9 +6,9 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND,
NULL_UUID, enableDispatcherModule, disableDispatcherModule, makeRunningValues, enableDispatcherModule, disableDispatcherModule, makeRunningValues,
Messages, Quat, Vec3, getControllerWorldLocation, makeDispatcherModuleParameters, Overlays, ZERO_VEC, Messages, Quat, Vec3, getControllerWorldLocation, makeDispatcherModuleParameters, Overlays, ZERO_VEC,
AVATAR_SELF_ID, HMD, INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, Settings, getGrabPointSphereOffset, HMD, INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, Settings, getGrabPointSphereOffset,
getEnabledModuleByName getEnabledModuleByName
*/ */
@ -172,7 +172,7 @@ Script.include("/~/system/libraries/controllers.js");
visible: true, visible: true,
ignoreRayIntersection: true, ignoreRayIntersection: true,
drawInFront: false, drawInFront: false,
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
parentJointIndex: MyAvatar.getJointIndex(this.hand === RIGHT_HAND ? parentJointIndex: MyAvatar.getJointIndex(this.hand === RIGHT_HAND ?
"_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" :
"_CAMERA_RELATIVE_CONTROLLER_LEFTHAND") "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND")
@ -288,7 +288,7 @@ Script.include("/~/system/libraries/controllers.js");
} }
// add the tabletScreen, if it is valid // add the tabletScreen, if it is valid
if (HMD.tabletScreenID && HMD.tabletScreenID !== NULL_UUID && if (HMD.tabletScreenID && HMD.tabletScreenID !== Uuid.NULL &&
Overlays.getProperty(HMD.tabletScreenID, "visible")) { Overlays.getProperty(HMD.tabletScreenID, "visible")) {
stylusTarget = TouchEventUtils.calculateTouchTargetFromOverlay(this.stylusTip, HMD.tabletScreenID); stylusTarget = TouchEventUtils.calculateTouchTargetFromOverlay(this.stylusTip, HMD.tabletScreenID);
if (stylusTarget) { if (stylusTarget) {
@ -297,7 +297,7 @@ Script.include("/~/system/libraries/controllers.js");
} }
// add the tablet home button. // add the tablet home button.
if (HMD.homeButtonID && HMD.homeButtonID !== NULL_UUID && if (HMD.homeButtonID && HMD.homeButtonID !== Uuid.NULL &&
Overlays.getProperty(HMD.homeButtonID, "visible")) { Overlays.getProperty(HMD.homeButtonID, "visible")) {
stylusTarget = TouchEventUtils.calculateTouchTargetFromOverlay(this.stylusTip, HMD.homeButtonID); stylusTarget = TouchEventUtils.calculateTouchTargetFromOverlay(this.stylusTip, HMD.homeButtonID);
if (stylusTarget) { if (stylusTarget) {

View file

@ -10,7 +10,7 @@
/* jslint bitwise: true */ /* jslint bitwise: true */
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, AVATAR_SELF_ID, getControllerJointIndex, NULL_UUID, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, getControllerJointIndex,
enableDispatcherModule, disableDispatcherModule, Messages, makeDispatcherModuleParameters, makeRunningValues, Vec3, enableDispatcherModule, disableDispatcherModule, Messages, makeDispatcherModuleParameters, makeRunningValues, Vec3,
LaserPointers, RayPick, HMD, Uuid, AvatarList LaserPointers, RayPick, HMD, Uuid, AvatarList
*/ */
@ -107,6 +107,7 @@ Script.include("/~/system/libraries/controllers.js");
ignoreRayIntersection: true ignoreRayIntersection: true
}; };
var teleportRenderStates = [{name: "cancel", path: cancelPath, end: cancelEnd}, var teleportRenderStates = [{name: "cancel", path: cancelPath, end: cancelEnd},
{name: "teleport", path: teleportPath, end: teleportEnd}, {name: "teleport", path: teleportPath, end: teleportEnd},
{name: "seat", path: seatPath, end: seatEnd}]; {name: "seat", path: seatPath, end: seatEnd}];
@ -117,6 +118,7 @@ Script.include("/~/system/libraries/controllers.js");
var coolInTimeout = null; var coolInTimeout = null;
var ignoredEntities = []; var ignoredEntities = [];
var TELEPORTER_STATES = { var TELEPORTER_STATES = {
IDLE: 'idle', IDLE: 'idle',
COOL_IN: 'cool_in', COOL_IN: 'cool_in',

View file

@ -8,15 +8,17 @@
/* jslint bitwise: true */ /* jslint bitwise: true */
/* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Vec3, Quat, getGrabPointSphereOffset, /* global Script, Controller, LaserPointers, RayPick, RIGHT_HAND, LEFT_HAND, Vec3, Quat, getGrabPointSphereOffset,
makeRunningValues, Entities, NULL_UUID, enableDispatcherModule, disableDispatcherModule, makeDispatcherModuleParameters, makeRunningValues, Entities, enableDispatcherModule, disableDispatcherModule, makeDispatcherModuleParameters,
PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD, PICK_MAX_DISTANCE, COLORS_GRAB_SEARCHING_HALF_SQUEEZE, COLORS_GRAB_SEARCHING_FULL_SQUEEZE, COLORS_GRAB_DISTANCE_HOLD,
AVATAR_SELF_ID, DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE, ZERO_VEC, Overlays DEFAULT_SEARCH_SPHERE_DISTANCE, TRIGGER_ON_VALUE, ZERO_VEC, Overlays
*/ */
Script.include("/~/system/libraries/controllerDispatcherUtils.js"); Script.include("/~/system/libraries/controllerDispatcherUtils.js");
Script.include("/~/system/libraries/controllers.js"); Script.include("/~/system/libraries/controllers.js");
(function() { (function() {
var END_RADIUS = 0.005;
var dim = { x: END_RADIUS, y: END_RADIUS, z: END_RADIUS };
var halfPath = { var halfPath = {
type: "line3d", type: "line3d",
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
@ -27,10 +29,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var halfEnd = { var halfEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE, color: COLORS_GRAB_SEARCHING_HALF_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -48,10 +51,11 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var fullEnd = { var fullEnd = {
type: "sphere", type: "sphere",
dimensions: dim,
solid: true, solid: true,
color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE, color: COLORS_GRAB_SEARCHING_FULL_SQUEEZE,
alpha: 0.9, alpha: 0.9,
@ -69,7 +73,7 @@ Script.include("/~/system/libraries/controllers.js");
lineWidth: 5, lineWidth: 5,
ignoreRayIntersection: true, // always ignore this ignoreRayIntersection: true, // always ignore this
drawInFront: true, // Even when burried inside of something, show it. drawInFront: true, // Even when burried inside of something, show it.
parentID: AVATAR_SELF_ID parentID: MyAvatar.SELF_ID
}; };
var renderStates = [ var renderStates = [
@ -90,15 +94,15 @@ Script.include("/~/system/libraries/controllers.js");
var HAPTIC_STYLUS_DURATION = 20.0; var HAPTIC_STYLUS_DURATION = 20.0;
function laserTargetHasKeyboardFocus(laserTarget) { function laserTargetHasKeyboardFocus(laserTarget) {
if (laserTarget && laserTarget !== NULL_UUID) { if (laserTarget && laserTarget !== Uuid.NULL) {
return Entities.keyboardFocusOverlay === laserTarget; return Entities.keyboardFocusOverlay === laserTarget;
} }
} }
function setKeyboardFocusOnLaserTarget(laserTarget) { function setKeyboardFocusOnLaserTarget(laserTarget) {
if (laserTarget && laserTarget !== NULL_UUID) { if (laserTarget && laserTarget !== Uuid.NULL) {
Entities.wantsHandControllerPointerEvents(laserTarget); Entities.wantsHandControllerPointerEvents(laserTarget);
Overlays.keyboardFocusOverlay = NULL_UUID; Overlays.keyboardFocusOverlay = Uuid.NULL;
Entities.keyboardFocusEntity = laserTarget; Entities.keyboardFocusEntity = laserTarget;
} }
} }
@ -117,7 +121,7 @@ Script.include("/~/system/libraries/controllers.js");
button: "None" button: "None"
}; };
if (laserTarget.entityID && laserTarget.entityID !== NULL_UUID) { if (laserTarget.entityID && laserTarget.entityID !== Uuid.NULL) {
Entities.sendHoverEnterEntity(laserTarget.entityID, pointerEvent); Entities.sendHoverEnterEntity(laserTarget.entityID, pointerEvent);
} }
} }
@ -137,7 +141,7 @@ Script.include("/~/system/libraries/controllers.js");
button: "None" button: "None"
}; };
if (laserTarget.entityID && laserTarget.entityID !== NULL_UUID) { if (laserTarget.entityID && laserTarget.entityID !== Uuid.NULL) {
Entities.sendMouseMoveOnEntity(laserTarget.entityID, pointerEvent); Entities.sendMouseMoveOnEntity(laserTarget.entityID, pointerEvent);
Entities.sendHoverOverEntity(laserTarget.entityID, pointerEvent); Entities.sendHoverOverEntity(laserTarget.entityID, pointerEvent);
} }
@ -156,7 +160,7 @@ Script.include("/~/system/libraries/controllers.js");
isPrimaryHeld: true isPrimaryHeld: true
}; };
if (laserTarget.entityID && laserTarget.entityID !== NULL_UUID) { if (laserTarget.entityID && laserTarget.entityID !== Uuid.NULL) {
Entities.sendMousePressOnEntity(laserTarget.entityID, pointerEvent); Entities.sendMousePressOnEntity(laserTarget.entityID, pointerEvent);
Entities.sendClickDownOnEntity(laserTarget.entityID, pointerEvent); Entities.sendClickDownOnEntity(laserTarget.entityID, pointerEvent);
} }
@ -173,7 +177,7 @@ Script.include("/~/system/libraries/controllers.js");
button: "Primary" button: "Primary"
}; };
if (laserTarget.entityID && laserTarget.entityID !== NULL_UUID) { if (laserTarget.entityID && laserTarget.entityID !== Uuid.NULL) {
Entities.sendMouseReleaseOnEntity(laserTarget.entityID, pointerEvent); Entities.sendMouseReleaseOnEntity(laserTarget.entityID, pointerEvent);
Entities.sendClickReleaseOnEntity(laserTarget.entityID, pointerEvent); Entities.sendClickReleaseOnEntity(laserTarget.entityID, pointerEvent);
Entities.sendHoverLeaveEntity(laserTarget.entityID, pointerEvent); Entities.sendHoverLeaveEntity(laserTarget.entityID, pointerEvent);
@ -192,7 +196,7 @@ Script.include("/~/system/libraries/controllers.js");
isPrimaryHeld: true isPrimaryHeld: true
}; };
if (laserTarget.entityID && laserTarget.entityID !== NULL_UUID) { if (laserTarget.entityID && laserTarget.entityID !== Uuid.NULL) {
Entities.sendMouseMoveOnEntity(laserTarget.entityID, pointerEvent); Entities.sendMouseMoveOnEntity(laserTarget.entityID, pointerEvent);
Entities.sendHoldingClickOnEntity(laserTarget.entityID, pointerEvent); Entities.sendHoldingClickOnEntity(laserTarget.entityID, pointerEvent);
} }
@ -366,17 +370,6 @@ Script.include("/~/system/libraries/controllers.js");
}; };
this.updateLaserPointer = function(controllerData) { this.updateLaserPointer = function(controllerData) {
var RADIUS = 0.005;
var dim = { x: RADIUS, y: RADIUS, z: RADIUS };
if (this.mode === "full") {
fullEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: fullPath, end: fullEnd});
} else if (this.mode === "half") {
halfEnd.dimensions = dim;
LaserPointers.editRenderState(this.laserPointer, this.mode, {path: halfPath, end: halfEnd});
}
LaserPointers.enableLaserPointer(this.laserPointer); LaserPointers.enableLaserPointer(this.laserPointer);
LaserPointers.setRenderState(this.laserPointer, this.mode); LaserPointers.setRenderState(this.laserPointer, this.mode);
}; };

View file

@ -1360,7 +1360,7 @@ function unparentSelectedEntities() {
} }
selectedEntities.forEach(function (id, index) { selectedEntities.forEach(function (id, index) {
var parentId = Entities.getEntityProperties(id, ["parentID"]).parentID; var parentId = Entities.getEntityProperties(id, ["parentID"]).parentID;
if (parentId !== null && parentId.length > 0 && parentId !== "{00000000-0000-0000-0000-000000000000}") { if (parentId !== null && parentId.length > 0 && parentId !== Uuid.NULL) {
parentCheck = true; parentCheck = true;
} }
Entities.editEntity(id, {parentID: null}); Entities.editEntity(id, {parentID: null});
@ -1476,10 +1476,19 @@ function onFileSaveChanged(filename) {
function onFileOpenChanged(filename) { function onFileOpenChanged(filename) {
// disconnect the event, otherwise the requests will stack up // disconnect the event, otherwise the requests will stack up
Window.openFileChanged.disconnect(onFileOpenChanged); try {
// Not all calls to onFileOpenChanged() connect an event.
Window.openFileChanged.disconnect(onFileOpenChanged);
} catch (e) {
// Ignore.
}
var importURL = null; var importURL = null;
if (filename !== "") { if (filename !== "") {
importURL = "file:///" + filename; importURL = filename;
if (!/^(http|https):\/\//.test(filename)) {
importURL = "file:///" + importURL;
}
} }
if (importURL) { if (importURL) {
if (!isActive && (Entities.canRez() && Entities.canRezTmp())) { if (!isActive && (Entities.canRez() && Entities.canRezTmp())) {

View file

@ -68,6 +68,7 @@ For usage and examples: colpick.com/plugin
cal.data('colpick').color = col = hexToHsb(fixHex(this.value)); cal.data('colpick').color = col = hexToHsb(fixHex(this.value));
fillRGBFields(col, cal.get(0)); fillRGBFields(col, cal.get(0));
fillHSBFields(col, cal.get(0)); fillHSBFields(col, cal.get(0));
fillHexFields(col, cal.get(0));
} else if (this.parentNode.className.indexOf('_hsb') > 0) { } else if (this.parentNode.className.indexOf('_hsb') > 0) {
cal.data('colpick').color = col = fixHSB({ cal.data('colpick').color = col = fixHSB({
h: parseInt(cal.data('colpick').fields.eq(4).val(), 10), h: parseInt(cal.data('colpick').fields.eq(4).val(), 10),
@ -76,6 +77,7 @@ For usage and examples: colpick.com/plugin
}); });
fillRGBFields(col, cal.get(0)); fillRGBFields(col, cal.get(0));
fillHexFields(col, cal.get(0)); fillHexFields(col, cal.get(0));
fillHSBFields(col, cal.get(0));
} else { } else {
cal.data('colpick').color = col = rgbToHsb(fixRGB({ cal.data('colpick').color = col = rgbToHsb(fixRGB({
r: parseInt(cal.data('colpick').fields.eq(1).val(), 10), r: parseInt(cal.data('colpick').fields.eq(1).val(), 10),
@ -84,6 +86,7 @@ For usage and examples: colpick.com/plugin
})); }));
fillHexFields(col, cal.get(0)); fillHexFields(col, cal.get(0));
fillHSBFields(col, cal.get(0)); fillHSBFields(col, cal.get(0));
fillRGBFields(col, cal.get(0));
} }
setSelector(col, cal.get(0)); setSelector(col, cal.get(0));
setHue(col, cal.get(0)); setHue(col, cal.get(0));

View file

@ -140,6 +140,10 @@
if (!$('body').hasClass("login-injected") && !userIsLoggedIn) { if (!$('body').hasClass("login-injected") && !userIsLoggedIn) {
$('body').addClass("login-injected"); $('body').addClass("login-injected");
var resultsElement = document.getElementById('results'); var resultsElement = document.getElementById('results');
if (!resultsElement) { // If we're on the main page, this will evaluate to `true`
resultsElement = document.getElementById('item-show');
resultsElement.style = 'margin-top:0;';
}
var logInElement = document.createElement('div'); var logInElement = document.createElement('div');
logInElement.classList.add("row"); logInElement.classList.add("row");
logInElement.id = "logInDiv"; logInElement.id = "logInDiv";
@ -193,6 +197,11 @@
var navbarBrandElement = document.getElementsByClassName('navbar-brand')[0]; var navbarBrandElement = document.getElementsByClassName('navbar-brand')[0];
var purchasesElement = document.createElement('a'); var purchasesElement = document.createElement('a');
var dropDownElement = document.getElementById('user-dropdown'); var dropDownElement = document.getElementById('user-dropdown');
$('#user-dropdown').find('.username')[0].style = "max-width:80px;white-space:nowrap;overflow:hidden;" +
"text-overflow:ellipsis;display:inline-block;position:relative;top:4px;";
$('#user-dropdown').find('.caret')[0].style = "position:relative;top:-3px;";
purchasesElement.id = "purchasesButton"; purchasesElement.id = "purchasesButton";
purchasesElement.setAttribute('href', "#"); purchasesElement.setAttribute('href', "#");
purchasesElement.innerHTML = "My Purchases"; purchasesElement.innerHTML = "My Purchases";

View file

@ -25,7 +25,6 @@ var ROT_LANDSCAPE = {x: 1.0, y: 1.0, z: 0, w: 0};
var ROT_LANDSCAPE_WINDOW = {x: 0.0, y: 0.0, z: 0.0, w: 0}; var ROT_LANDSCAPE_WINDOW = {x: 0.0, y: 0.0, z: 0.0, w: 0};
var TABLET_TEXTURE_RESOLUTION = { x: 480, y: 706 }; var TABLET_TEXTURE_RESOLUTION = { x: 480, y: 706 };
var INCHES_TO_METERS = 1 / 39.3701; var INCHES_TO_METERS = 1 / 39.3701;
var AVATAR_SELF_ID = "{00000000-0000-0000-0000-000000000001}";
var NO_HANDS = -1; var NO_HANDS = -1;
var DELAY_FOR_30HZ = 33; // milliseconds var DELAY_FOR_30HZ = 33; // milliseconds
@ -100,7 +99,7 @@ WebTablet = function (url, width, dpi, hand, clientOnly, location, visible) {
"grabbableKey": {"grabbable": true} "grabbableKey": {"grabbable": true}
}), }),
dimensions: { x: tabletWidth, y: tabletHeight, z: tabletDepth }, dimensions: { x: tabletWidth, y: tabletHeight, z: tabletDepth },
parentID: AVATAR_SELF_ID, parentID: MyAvatar.SELF_ID,
visible: visible visible: visible
}; };
@ -471,7 +470,7 @@ WebTablet.prototype.register = function() {
WebTablet.prototype.cleanUpOldTabletsOnJoint = function(jointIndex) { WebTablet.prototype.cleanUpOldTabletsOnJoint = function(jointIndex) {
var children = Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, jointIndex); var children = Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, jointIndex);
children = children.concat(Entities.getChildrenIDsOfJoint(AVATAR_SELF_ID, jointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.SELF_ID, jointIndex));
children.forEach(function(childID) { children.forEach(function(childID) {
var props = Entities.getEntityProperties(childID, ["name"]); var props = Entities.getEntityProperties(childID, ["name"]);
if (props.name === "WebTablet Tablet") { if (props.name === "WebTablet Tablet") {

View file

@ -7,7 +7,7 @@
/* global module, Camera, HMD, MyAvatar, controllerDispatcherPlugins:true, Quat, Vec3, Overlays, Xform, /* global module, Camera, HMD, MyAvatar, controllerDispatcherPlugins:true, Quat, Vec3, Overlays, Xform,
MSECS_PER_SEC:true , LEFT_HAND:true, RIGHT_HAND:true, NULL_UUID:true, AVATAR_SELF_ID:true, FORBIDDEN_GRAB_TYPES:true, MSECS_PER_SEC:true , LEFT_HAND:true, RIGHT_HAND:true, FORBIDDEN_GRAB_TYPES:true,
HAPTIC_PULSE_STRENGTH:true, HAPTIC_PULSE_DURATION:true, ZERO_VEC:true, ONE_VEC:true, HAPTIC_PULSE_STRENGTH:true, HAPTIC_PULSE_DURATION:true, ZERO_VEC:true, ONE_VEC:true,
DEFAULT_REGISTRATION_POINT:true, INCHES_TO_METERS:true, DEFAULT_REGISTRATION_POINT:true, INCHES_TO_METERS:true,
TRIGGER_OFF_VALUE:true, TRIGGER_OFF_VALUE:true,
@ -60,9 +60,6 @@ ONE_VEC = { x: 1, y: 1, z: 1 };
LEFT_HAND = 0; LEFT_HAND = 0;
RIGHT_HAND = 1; RIGHT_HAND = 1;
NULL_UUID = "{00000000-0000-0000-0000-000000000000}";
AVATAR_SELF_ID = "{00000000-0000-0000-0000-000000000001}";
FORBIDDEN_GRAB_TYPES = ["Unknown", "Light", "PolyLine", "Zone"]; FORBIDDEN_GRAB_TYPES = ["Unknown", "Light", "PolyLine", "Zone"];
HAPTIC_PULSE_STRENGTH = 1.0; HAPTIC_PULSE_STRENGTH = 1.0;
@ -284,7 +281,7 @@ ensureDynamic = function (entityID) {
// if we distance hold something and keep it very still before releasing it, it ends up // if we distance hold something and keep it very still before releasing it, it ends up
// non-dynamic in bullet. If it's too still, give it a little bounce so it will fall. // non-dynamic in bullet. If it's too still, give it a little bounce so it will fall.
var props = Entities.getEntityProperties(entityID, ["velocity", "dynamic", "parentID"]); var props = Entities.getEntityProperties(entityID, ["velocity", "dynamic", "parentID"]);
if (props.dynamic && props.parentID === NULL_UUID) { if (props.dynamic && props.parentID === Uuid.NULL) {
var velocity = props.velocity; var velocity = props.velocity;
if (Vec3.length(velocity) < 0.05) { // see EntityMotionState.cpp DYNAMIC_LINEAR_VELOCITY_THRESHOLD if (Vec3.length(velocity) < 0.05) { // see EntityMotionState.cpp DYNAMIC_LINEAR_VELOCITY_THRESHOLD
velocity = { x: 0.0, y: 0.2, z: 0.0 }; velocity = { x: 0.0, y: 0.2, z: 0.0 };
@ -295,7 +292,7 @@ ensureDynamic = function (entityID) {
findGroupParent = function (controllerData, targetProps) { findGroupParent = function (controllerData, targetProps) {
while (targetProps.parentID && while (targetProps.parentID &&
targetProps.parentID !== NULL_UUID && targetProps.parentID !== Uuid.NULL &&
Entities.getNestableType(targetProps.parentID) == "entity") { Entities.getNestableType(targetProps.parentID) == "entity") {
var parentProps = Entities.getEntityProperties(targetProps.parentID, DISPATCHER_PROPERTIES); var parentProps = Entities.getEntityProperties(targetProps.parentID, DISPATCHER_PROPERTIES);
if (!parentProps) { if (!parentProps) {
@ -314,19 +311,19 @@ findHandChildEntities = function(hand) {
// find children of avatar's hand joint // find children of avatar's hand joint
var handJointIndex = MyAvatar.getJointIndex(hand === RIGHT_HAND ? "RightHand" : "LeftHand"); var handJointIndex = MyAvatar.getJointIndex(hand === RIGHT_HAND ? "RightHand" : "LeftHand");
var children = Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, handJointIndex); var children = Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, handJointIndex);
children = children.concat(Entities.getChildrenIDsOfJoint(AVATAR_SELF_ID, handJointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.SELF_ID, handJointIndex));
// find children of faux controller joint // find children of faux controller joint
var controllerJointIndex = getControllerJointIndex(hand); var controllerJointIndex = getControllerJointIndex(hand);
children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, controllerJointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, controllerJointIndex));
children = children.concat(Entities.getChildrenIDsOfJoint(AVATAR_SELF_ID, controllerJointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.SELF_ID, controllerJointIndex));
// find children of faux camera-relative controller joint // find children of faux camera-relative controller joint
var controllerCRJointIndex = MyAvatar.getJointIndex(hand === RIGHT_HAND ? var controllerCRJointIndex = MyAvatar.getJointIndex(hand === RIGHT_HAND ?
"_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" : "_CAMERA_RELATIVE_CONTROLLER_RIGHTHAND" :
"_CAMERA_RELATIVE_CONTROLLER_LEFTHAND"); "_CAMERA_RELATIVE_CONTROLLER_LEFTHAND");
children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, controllerCRJointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.sessionUUID, controllerCRJointIndex));
children = children.concat(Entities.getChildrenIDsOfJoint(AVATAR_SELF_ID, controllerCRJointIndex)); children = children.concat(Entities.getChildrenIDsOfJoint(MyAvatar.SELF_ID, controllerCRJointIndex));
return children.filter(function (childID) { return children.filter(function (childID) {
var childType = Entities.getNestableType(childID); var childType = Entities.getNestableType(childID);

View file

@ -118,20 +118,12 @@ CameraManager = function() {
that.targetYaw = 0; that.targetYaw = 0;
that.targetPitch = 0; that.targetPitch = 0;
that.focalPoint = { that.focalPoint = Vec3.ZERO;
x: 0, that.targetFocalPoint = Vec3.ZERO;
y: 0,
z: 0
};
that.targetFocalPoint = {
x: 0,
y: 0,
z: 0
};
easing = false; easing = false;
easingTime = 0; easingTime = 0;
startOrientation = Quat.fromPitchYawRollDegrees(0, 0, 0); startOrientation = Quat.IDENTITY;
that.previousCameraMode = null; that.previousCameraMode = null;

View file

@ -71,44 +71,16 @@ SelectionManager = (function() {
that.selections = []; that.selections = [];
var listeners = []; var listeners = [];
that.localRotation = Quat.fromPitchYawRollDegrees(0, 0, 0); that.localRotation = Quat.IDENTITY;
that.localPosition = { that.localPosition = Vec3.ZERO;
x: 0, that.localDimensions = Vec3.ZERO;
y: 0, that.localRegistrationPoint = Vec3.HALF;
z: 0
};
that.localDimensions = {
x: 0,
y: 0,
z: 0
};
that.localRegistrationPoint = {
x: 0.5,
y: 0.5,
z: 0.5
};
that.worldRotation = Quat.fromPitchYawRollDegrees(0, 0, 0); that.worldRotation = Quat.IDENTITY;
that.worldPosition = { that.worldPosition = Vec3.ZERO;
x: 0, that.worldDimensions = Vec3.ZERO;
y: 0, that.worldRegistrationPoint = Vec3.HALF;
z: 0 that.centerPosition = Vec3.ZERO;
};
that.worldDimensions = {
x: 0,
y: 0,
z: 0
};
that.worldRegistrationPoint = {
x: 0.5,
y: 0.5,
z: 0.5
};
that.centerPosition = {
x: 0,
y: 0,
z: 0
};
that.saveProperties = function() { that.saveProperties = function() {
that.savedProperties = {}; that.savedProperties = {};
@ -350,11 +322,7 @@ SelectionDisplay = (function() {
}; };
var grabberLineWidth = 0.5; var grabberLineWidth = 0.5;
var grabberSolid = true; var grabberSolid = true;
var grabberMoveUpPosition = { var grabberMoveUpPosition = Vec3.ZERO;
x: 0,
y: 0,
z: 0
};
var lightOverlayColor = { var lightOverlayColor = {
red: 255, red: 255,
@ -363,11 +331,7 @@ SelectionDisplay = (function() {
}; };
var grabberPropertiesCorner = { var grabberPropertiesCorner = {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: grabberSizeCorner, size: grabberSizeCorner,
color: grabberColorCorner, color: grabberColorCorner,
alpha: 1, alpha: 1,
@ -380,11 +344,7 @@ SelectionDisplay = (function() {
}; };
var grabberPropertiesEdge = { var grabberPropertiesEdge = {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: grabberSizeEdge, size: grabberSizeEdge,
color: grabberColorEdge, color: grabberColorEdge,
alpha: 1, alpha: 1,
@ -397,11 +357,7 @@ SelectionDisplay = (function() {
}; };
var grabberPropertiesFace = { var grabberPropertiesFace = {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: grabberSizeFace, size: grabberSizeFace,
color: grabberColorFace, color: grabberColorFace,
alpha: 1, alpha: 1,
@ -414,11 +370,7 @@ SelectionDisplay = (function() {
}; };
var grabberPropertiesCloner = { var grabberPropertiesCloner = {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: grabberSizeCorner, size: grabberSizeCorner,
color: grabberColorCloner, color: grabberColorCloner,
alpha: 1, alpha: 1,
@ -436,11 +388,7 @@ SelectionDisplay = (function() {
}; };
var highlightBox = Overlays.addOverlay("cube", { var highlightBox = Overlays.addOverlay("cube", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: 1, size: 1,
color: { color: {
red: 90, red: 90,
@ -457,11 +405,7 @@ SelectionDisplay = (function() {
}); });
var selectionBox = Overlays.addOverlay("cube", { var selectionBox = Overlays.addOverlay("cube", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: 1, size: 1,
color: { color: {
red: 255, red: 255,
@ -478,11 +422,7 @@ SelectionDisplay = (function() {
var selectionBoxes = []; var selectionBoxes = [];
var rotationDegreesDisplay = Overlays.addOverlay("text3d", { var rotationDegreesDisplay = Overlays.addOverlay("text3d", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
text: "", text: "",
color: { color: {
red: 0, red: 0,
@ -513,11 +453,7 @@ SelectionDisplay = (function() {
var grabberMoveUp = Overlays.addOverlay("image3d", { var grabberMoveUp = Overlays.addOverlay("image3d", {
url: HIFI_PUBLIC_BUCKET + "images/up-arrow.svg", url: HIFI_PUBLIC_BUCKET + "images/up-arrow.svg",
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
color: handleColor, color: handleColor,
alpha: handleAlpha, alpha: handleAlpha,
visible: false, visible: false,
@ -720,16 +656,8 @@ SelectionDisplay = (function() {
var xRailOverlay = Overlays.addOverlay("line3d", { var xRailOverlay = Overlays.addOverlay("line3d", {
visible: false, visible: false,
lineWidth: 1.0, lineWidth: 1.0,
start: { start: Vec3.ZERO,
x: 0, end: Vec3.ZERO,
y: 0,
z: 0
},
end: {
x: 0,
y: 0,
z: 0
},
color: { color: {
red: 255, red: 255,
green: 0, green: 0,
@ -740,16 +668,8 @@ SelectionDisplay = (function() {
var yRailOverlay = Overlays.addOverlay("line3d", { var yRailOverlay = Overlays.addOverlay("line3d", {
visible: false, visible: false,
lineWidth: 1.0, lineWidth: 1.0,
start: { start: Vec3.ZERO,
x: 0, end: Vec3.ZERO,
y: 0,
z: 0
},
end: {
x: 0,
y: 0,
z: 0
},
color: { color: {
red: 0, red: 0,
green: 255, green: 255,
@ -760,16 +680,8 @@ SelectionDisplay = (function() {
var zRailOverlay = Overlays.addOverlay("line3d", { var zRailOverlay = Overlays.addOverlay("line3d", {
visible: false, visible: false,
lineWidth: 1.0, lineWidth: 1.0,
start: { start: Vec3.ZERO,
x: 0, end: Vec3.ZERO,
y: 0,
z: 0
},
end: {
x: 0,
y: 0,
z: 0
},
color: { color: {
red: 0, red: 0,
green: 0, green: 0,
@ -781,16 +693,8 @@ SelectionDisplay = (function() {
var rotateZeroOverlay = Overlays.addOverlay("line3d", { var rotateZeroOverlay = Overlays.addOverlay("line3d", {
visible: false, visible: false,
lineWidth: 2.0, lineWidth: 2.0,
start: { start: Vec3.ZERO,
x: 0, end: Vec3.ZERO,
y: 0,
z: 0
},
end: {
x: 0,
y: 0,
z: 0
},
color: { color: {
red: 255, red: 255,
green: 0, green: 0,
@ -802,16 +706,8 @@ SelectionDisplay = (function() {
var rotateCurrentOverlay = Overlays.addOverlay("line3d", { var rotateCurrentOverlay = Overlays.addOverlay("line3d", {
visible: false, visible: false,
lineWidth: 2.0, lineWidth: 2.0,
start: { start: Vec3.ZERO,
x: 0, end: Vec3.ZERO,
y: 0,
z: 0
},
end: {
x: 0,
y: 0,
z: 0
},
color: { color: {
red: 0, red: 0,
green: 0, green: 0,
@ -822,11 +718,7 @@ SelectionDisplay = (function() {
var rotateOverlayInner = Overlays.addOverlay("circle3d", { var rotateOverlayInner = Overlays.addOverlay("circle3d", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: 1, size: 1,
color: { color: {
red: 51, red: 51,
@ -856,11 +748,7 @@ SelectionDisplay = (function() {
}); });
var rotateOverlayOuter = Overlays.addOverlay("circle3d", { var rotateOverlayOuter = Overlays.addOverlay("circle3d", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: 1, size: 1,
color: { color: {
red: 51, red: 51,
@ -891,11 +779,7 @@ SelectionDisplay = (function() {
}); });
var rotateOverlayCurrent = Overlays.addOverlay("circle3d", { var rotateOverlayCurrent = Overlays.addOverlay("circle3d", {
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
size: 1, size: 1,
color: { color: {
red: 224, red: 224,
@ -922,11 +806,7 @@ SelectionDisplay = (function() {
var yawHandle = Overlays.addOverlay("image3d", { var yawHandle = Overlays.addOverlay("image3d", {
url: ROTATE_ARROW_WEST_NORTH_URL, url: ROTATE_ARROW_WEST_NORTH_URL,
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
color: handleColor, color: handleColor,
alpha: handleAlpha, alpha: handleAlpha,
visible: false, visible: false,
@ -939,11 +819,7 @@ SelectionDisplay = (function() {
var pitchHandle = Overlays.addOverlay("image3d", { var pitchHandle = Overlays.addOverlay("image3d", {
url: ROTATE_ARROW_WEST_NORTH_URL, url: ROTATE_ARROW_WEST_NORTH_URL,
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
color: handleColor, color: handleColor,
alpha: handleAlpha, alpha: handleAlpha,
visible: false, visible: false,
@ -956,11 +832,7 @@ SelectionDisplay = (function() {
var rollHandle = Overlays.addOverlay("image3d", { var rollHandle = Overlays.addOverlay("image3d", {
url: ROTATE_ARROW_WEST_NORTH_URL, url: ROTATE_ARROW_WEST_NORTH_URL,
position: { position: Vec3.ZERO,
x: 0,
y: 0,
z: 0
},
color: handleColor, color: handleColor,
alpha: handleAlpha, alpha: handleAlpha,
visible: false, visible: false,
@ -1636,7 +1508,7 @@ SelectionDisplay = (function() {
position = SelectionManager.localPosition; position = SelectionManager.localPosition;
registrationPoint = SelectionManager.localRegistrationPoint; registrationPoint = SelectionManager.localRegistrationPoint;
} else { } else {
rotation = Quat.fromPitchYawRollDegrees(0, 0, 0); rotation = Quat.IDENTITY;
dimensions = SelectionManager.worldDimensions; dimensions = SelectionManager.worldDimensions;
position = SelectionManager.worldPosition; position = SelectionManager.worldPosition;
registrationPoint = SelectionManager.worldRegistrationPoint; registrationPoint = SelectionManager.worldRegistrationPoint;
@ -2692,7 +2564,7 @@ SelectionDisplay = (function() {
var onBegin = function(event, pickRay, pickResult) { var onBegin = function(event, pickRay, pickResult) {
var properties = Entities.getEntityProperties(SelectionManager.selections[0]); var properties = Entities.getEntityProperties(SelectionManager.selections[0]);
initialProperties = properties; initialProperties = properties;
rotation = (spaceMode === SPACE_LOCAL) ? properties.rotation : Quat.fromPitchYawRollDegrees(0, 0, 0); rotation = (spaceMode === SPACE_LOCAL) ? properties.rotation : Quat.IDENTITY;
if (spaceMode === SPACE_LOCAL) { if (spaceMode === SPACE_LOCAL) {
rotation = SelectionManager.localRotation; rotation = SelectionManager.localRotation;

View file

@ -18,7 +18,7 @@ OverlayGroup = function(opts) {
var overlays = {}; var overlays = {};
var rootPosition = opts.position || { x: 0, y: 0, z: 0 }; var rootPosition = opts.position || { x: 0, y: 0, z: 0 };
var rootRotation = opts.rotation || Quat.fromPitchYawRollRadians(0, 0, 0); var rootRotation = opts.rotation || Quat.IDENTITY;
var visible = opts.visible == true; var visible = opts.visible == true;
function updateOverlays() { function updateOverlays() {
@ -36,7 +36,7 @@ OverlayGroup = function(opts) {
that.createOverlay = function(type, properties) { that.createOverlay = function(type, properties) {
properties.position = properties.position || { x: 0, y: 0, z: 0 }; properties.position = properties.position || { x: 0, y: 0, z: 0 };
properties.rotation = properties.rotation || Quat.fromPitchYawRollRadians(0, 0, 0); properties.rotation = properties.rotation || Quat.IDENTITY;
var overlay = Overlays.addOverlay(type, properties); var overlay = Overlays.addOverlay(type, properties);

View file

@ -6,28 +6,28 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
/* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND, /* global Script, Entities, MyAvatar, Controller, RIGHT_HAND, LEFT_HAND,
controllerDispatcher.NULL_UUID, enableDispatcherModule, disableDispatcherModule, makeRunningValues, enableDispatcherModule, disableDispatcherModule, makeRunningValues,
Messages, Quat, Vec3, getControllerWorldLocation, makeDispatcherModuleParameters, Overlays, controllerDispatcher.ZERO_VEC, Messages, Quat, Vec3, getControllerWorldLocation, makeDispatcherModuleParameters, Overlays, controllerDispatcher.ZERO_VEC,
AVATAR_SELF_ID, HMD, INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, Settings, getGrabPointSphereOffset HMD, INCHES_TO_METERS, DEFAULT_REGISTRATION_POINT, Settings, getGrabPointSphereOffset
*/ */
var controllerDispatcher = Script.require("/~/system/libraries/controllerDispatcherUtils.js"); var controllerDispatcher = Script.require("/~/system/libraries/controllerDispatcherUtils.js");
function touchTargetHasKeyboardFocus(touchTarget) { function touchTargetHasKeyboardFocus(touchTarget) {
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
return Entities.keyboardFocusEntity === touchTarget.entityID; return Entities.keyboardFocusEntity === touchTarget.entityID;
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
return Overlays.keyboardFocusOverlay === touchTarget.overlayID; return Overlays.keyboardFocusOverlay === touchTarget.overlayID;
} }
} }
function setKeyboardFocusOnTouchTarget(touchTarget) { function setKeyboardFocusOnTouchTarget(touchTarget) {
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID && if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL &&
Entities.wantsHandControllerPointerEvents(touchTarget.entityID)) { Entities.wantsHandControllerPointerEvents(touchTarget.entityID)) {
Overlays.keyboardFocusOverlay = controllerDispatcher.NULL_UUID; Overlays.keyboardFocusOverlay = Uuid.NULL;
Entities.keyboardFocusEntity = touchTarget.entityID; Entities.keyboardFocusEntity = touchTarget.entityID;
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.keyboardFocusOverlay = touchTarget.overlayID; Overlays.keyboardFocusOverlay = touchTarget.overlayID;
Entities.keyboardFocusEntity = controllerDispatcher.NULL_UUID; Entities.keyboardFocusEntity = Uuid.NULL;
} }
} }
@ -42,9 +42,9 @@ function sendHoverEnterEventToTouchTarget(hand, touchTarget) {
button: "None" button: "None"
}; };
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
Entities.sendHoverEnterEntity(touchTarget.entityID, pointerEvent); Entities.sendHoverEnterEntity(touchTarget.entityID, pointerEvent);
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.sendHoverEnterOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendHoverEnterOverlay(touchTarget.overlayID, pointerEvent);
} }
} }
@ -60,10 +60,10 @@ function sendHoverOverEventToTouchTarget(hand, touchTarget) {
button: "None" button: "None"
}; };
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
Entities.sendMouseMoveOnEntity(touchTarget.entityID, pointerEvent); Entities.sendMouseMoveOnEntity(touchTarget.entityID, pointerEvent);
Entities.sendHoverOverEntity(touchTarget.entityID, pointerEvent); Entities.sendHoverOverEntity(touchTarget.entityID, pointerEvent);
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.sendMouseMoveOnOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendMouseMoveOnOverlay(touchTarget.overlayID, pointerEvent);
Overlays.sendHoverOverOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendHoverOverOverlay(touchTarget.overlayID, pointerEvent);
} }
@ -81,10 +81,10 @@ function sendTouchStartEventToTouchTarget(hand, touchTarget) {
isPrimaryHeld: true isPrimaryHeld: true
}; };
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
Entities.sendMousePressOnEntity(touchTarget.entityID, pointerEvent); Entities.sendMousePressOnEntity(touchTarget.entityID, pointerEvent);
Entities.sendClickDownOnEntity(touchTarget.entityID, pointerEvent); Entities.sendClickDownOnEntity(touchTarget.entityID, pointerEvent);
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.sendMousePressOnOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendMousePressOnOverlay(touchTarget.overlayID, pointerEvent);
} }
} }
@ -100,11 +100,11 @@ function sendTouchEndEventToTouchTarget(hand, touchTarget) {
button: "Primary" button: "Primary"
}; };
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
Entities.sendMouseReleaseOnEntity(touchTarget.entityID, pointerEvent); Entities.sendMouseReleaseOnEntity(touchTarget.entityID, pointerEvent);
Entities.sendClickReleaseOnEntity(touchTarget.entityID, pointerEvent); Entities.sendClickReleaseOnEntity(touchTarget.entityID, pointerEvent);
Entities.sendHoverLeaveEntity(touchTarget.entityID, pointerEvent); Entities.sendHoverLeaveEntity(touchTarget.entityID, pointerEvent);
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.sendMouseReleaseOnOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendMouseReleaseOnOverlay(touchTarget.overlayID, pointerEvent);
} }
} }
@ -121,10 +121,10 @@ function sendTouchMoveEventToTouchTarget(hand, touchTarget) {
isPrimaryHeld: true isPrimaryHeld: true
}; };
if (touchTarget.entityID && touchTarget.entityID !== controllerDispatcher.NULL_UUID) { if (touchTarget.entityID && touchTarget.entityID !== Uuid.NULL) {
Entities.sendMouseMoveOnEntity(touchTarget.entityID, pointerEvent); Entities.sendMouseMoveOnEntity(touchTarget.entityID, pointerEvent);
Entities.sendHoldingClickOnEntity(touchTarget.entityID, pointerEvent); Entities.sendHoldingClickOnEntity(touchTarget.entityID, pointerEvent);
} else if (touchTarget.overlayID && touchTarget.overlayID !== controllerDispatcher.NULL_UUID) { } else if (touchTarget.overlayID && touchTarget.overlayID !== Uuid.NULL) {
Overlays.sendMouseMoveOnOverlay(touchTarget.overlayID, pointerEvent); Overlays.sendMouseMoveOnOverlay(touchTarget.overlayID, pointerEvent);
} }
} }

View file

@ -13,7 +13,6 @@
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
const CLIENTONLY = false; const CLIENTONLY = false;
const NULL_UUID = "{00000000-0000-0000-0000-000000000000}";
const ENTITY_CHECK_INTERVAL = 5000; // ms = 5 seconds const ENTITY_CHECK_INTERVAL = 5000; // ms = 5 seconds
const STARTUP_DELAY = 2000; // ms = 2 second const STARTUP_DELAY = 2000; // ms = 2 second
const OLD_AGE = 3500; // we recreate the entity if older than this time in seconds const OLD_AGE = 3500; // we recreate the entity if older than this time in seconds
@ -24,7 +23,7 @@ const SIZE_Y = 0.075;
const LETTER_OFFSET = 0.03; // arbitrary value to dynamically change width, could be more accurate by detecting characters const LETTER_OFFSET = 0.03; // arbitrary value to dynamically change width, could be more accurate by detecting characters
const LINE_HEIGHT = 0.05; const LINE_HEIGHT = 0.05;
var nameTagEntityID = NULL_UUID; var nameTagEntityID = Uuid.NULL;
var lastCheckForEntity = 0; var lastCheckForEntity = 0;
// create the name tag entity after a brief delay // create the name tag entity after a brief delay
@ -62,9 +61,9 @@ function updateNameTag() {
}; };
function deleteNameTag() { function deleteNameTag() {
if(nameTagEntityID !== NULL_UUID) { if(nameTagEntityID !== Uuid.NULL) {
Entities.deleteEntity(nameTagEntityID); Entities.deleteEntity(nameTagEntityID);
nameTagEntityID = NULL_UUID; nameTagEntityID = Uuid.NULL;
} }
} }
@ -85,7 +84,7 @@ function cleanup() {
Script.update.connect(update); Script.update.connect(update);
function update() { function update() {
// if no entity we return // if no entity we return
if(nameTagEntityID == NULL_UUID) { if(nameTagEntityID == Uuid.NULL) {
return; return;
} }

View file

@ -576,7 +576,7 @@
createNotification("Processing GIF snapshot...", NotificationType.SNAPSHOT); createNotification("Processing GIF snapshot...", NotificationType.SNAPSHOT);
} }
function processingGif() { function walletNotSetup() {
createNotification("Your wallet isn't set up. Open the WALLET app.", NotificationType.WALLET); createNotification("Your wallet isn't set up. Open the WALLET app.", NotificationType.WALLET);
} }

View file

@ -14,7 +14,6 @@
// Distributed under the Apache License, Version 2.0. // Distributed under the Apache License, Version 2.0.
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
var NULL_UUID = "{00000000-0000-0000-0000-000000000000}";
var LIFETIME = 3600; var LIFETIME = 3600;
var BALL_SIZE = 0.175; var BALL_SIZE = 0.175;
var BALL_DAMPING = 0.5; var BALL_DAMPING = 0.5;

View file

@ -27,6 +27,7 @@ if (typeof Vec3.abs !== "function") {
} }
if (typeof Quat.ZERO !== "object") { if (typeof Quat.ZERO !== "object") {
// TODO: Change to Quat.IDENTITY.
Quat.ZERO = Quat.fromVec3Radians(Vec3.ZERO); Quat.ZERO = Quat.fromVec3Radians(Vec3.ZERO);
} }