mirror of
https://github.com/overte-org/overte.git
synced 2025-04-23 14:14:07 +02:00
Merge branch 'master' of https://github.com/highfidelity/hifi into sessionDisplayNames
This commit is contained in:
commit
9d9345cb65
74 changed files with 1200 additions and 523 deletions
assignment-client/src
domain-server/src
interface
resources/meshes/controller/touch
Oculus-Labels-L.fbxOculus-Labels-R.fbxtouch_l.fbxtouch_l_body.fbxtouch_l_bumper.fbxtouch_l_button_x.fbxtouch_l_button_y.fbxtouch_l_joystick.fbxtouch_l_trigger.fbxtouch_r.fbxtouch_r_body.fbxtouch_r_bumper.fbxtouch_r_button_a.fbxtouch_r_button_b.fbxtouch_r_joystick.fbxtouch_r_trigger.fbx
src
libraries
animation/src
audio-client/src
audio/src
display-plugins/src/display-plugins
entities-renderer/src
fbx/src
gl/src/gl
gpu-gl/src/gpu
gpu/src/gpu
model-networking/src/model-networking
model/src/model
networking/src
octree/src
plugins/src/plugins
render-utils/src
render/src/render
shared/src
plugins
scripts/system/controllers
controllerDisplay.jscontrollerDisplayManager.jstouchControllerConfiguration.jsviveControllerConfiguration.js
tests
tutorial
|
@ -38,6 +38,7 @@
|
|||
#include "AssignmentClientLogging.h"
|
||||
#include "avatars/ScriptableAvatar.h"
|
||||
#include <Trace.h>
|
||||
#include <StatTracker.h>
|
||||
|
||||
const QString ASSIGNMENT_CLIENT_TARGET_NAME = "assignment-client";
|
||||
const long long ASSIGNMENT_REQUEST_INTERVAL_MSECS = 1 * 1000;
|
||||
|
@ -50,6 +51,7 @@ AssignmentClient::AssignmentClient(Assignment::Type requestAssignmentType, QStri
|
|||
LogUtils::init();
|
||||
|
||||
DependencyManager::set<tracing::Tracer>();
|
||||
DependencyManager::set<StatTracker>();
|
||||
DependencyManager::set<AccountManager>();
|
||||
|
||||
auto scriptableAvatar = DependencyManager::set<ScriptableAvatar>();
|
||||
|
|
|
@ -44,6 +44,7 @@
|
|||
#include "DomainServerNodeData.h"
|
||||
#include "NodeConnectionData.h"
|
||||
#include <Trace.h>
|
||||
#include <StatTracker.h>
|
||||
|
||||
int const DomainServer::EXIT_CODE_REBOOT = 234923;
|
||||
|
||||
|
@ -75,6 +76,7 @@ DomainServer::DomainServer(int argc, char* argv[]) :
|
|||
parseCommandLine();
|
||||
|
||||
DependencyManager::set<tracing::Tracer>();
|
||||
DependencyManager::set<StatTracker>();
|
||||
|
||||
LogUtils::init();
|
||||
Setting::init();
|
||||
|
|
BIN
interface/resources/meshes/controller/touch/Oculus-Labels-L.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/Oculus-Labels-L.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/Oculus-Labels-R.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/Oculus-Labels-R.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_body.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_body.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_bumper.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_bumper.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_button_x.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_button_x.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_button_y.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_button_y.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_joystick.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_joystick.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_l_trigger.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_l_trigger.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_body.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_body.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_bumper.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_bumper.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_button_a.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_button_a.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_button_b.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_button_b.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_joystick.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_joystick.fbx
Normal file
Binary file not shown.
BIN
interface/resources/meshes/controller/touch/touch_r_trigger.fbx
Normal file
BIN
interface/resources/meshes/controller/touch/touch_r_trigger.fbx
Normal file
Binary file not shown.
|
@ -179,6 +179,8 @@ extern "C" {
|
|||
}
|
||||
#endif
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_app_input_mouse, "trace.app.input.mouse")
|
||||
|
||||
using namespace std;
|
||||
|
||||
static QTimer locationUpdateTimer;
|
||||
|
@ -1389,16 +1391,31 @@ Application::Application(int& argc, char** argv, QElapsedTimer& startupTimer, bo
|
|||
}
|
||||
qCDebug(interfaceapp) << "Server content version: " << contentVersion;
|
||||
|
||||
bool hasTutorialContent = contentVersion >= 1;
|
||||
static const int MIN_VIVE_CONTENT_VERSION = 1;
|
||||
static const int MIN_OCULUS_TOUCH_CONTENT_VERSION = 27;
|
||||
|
||||
bool hasSufficientTutorialContent = false;
|
||||
bool hasHandControllers = false;
|
||||
|
||||
// Only specific hand controllers are currently supported, so only send users to the tutorial
|
||||
// if they have one of those hand controllers.
|
||||
if (PluginUtils::isViveControllerAvailable()) {
|
||||
hasHandControllers = true;
|
||||
hasSufficientTutorialContent = contentVersion >= MIN_VIVE_CONTENT_VERSION;
|
||||
} else if (PluginUtils::isOculusTouchControllerAvailable()) {
|
||||
hasHandControllers = true;
|
||||
hasSufficientTutorialContent = contentVersion >= MIN_OCULUS_TOUCH_CONTENT_VERSION;
|
||||
}
|
||||
|
||||
Setting::Handle<bool> firstRun { Settings::firstRun, true };
|
||||
bool hasHMDAndHandControllers = PluginUtils::isHMDAvailable("OpenVR (Vive)") && PluginUtils::isHandControllerAvailable();
|
||||
|
||||
bool hasHMDAndHandControllers = PluginUtils::isHMDAvailable() && hasHandControllers;
|
||||
Setting::Handle<bool> tutorialComplete { "tutorialComplete", false };
|
||||
|
||||
bool shouldGoToTutorial = hasHMDAndHandControllers && hasTutorialContent && !tutorialComplete.get();
|
||||
bool shouldGoToTutorial = hasHMDAndHandControllers && hasSufficientTutorialContent && !tutorialComplete.get();
|
||||
|
||||
qCDebug(interfaceapp) << "Has HMD + Hand Controllers: " << hasHMDAndHandControllers << ", current plugin: " << _displayPlugin->getName();
|
||||
qCDebug(interfaceapp) << "Has tutorial content: " << hasTutorialContent;
|
||||
qCDebug(interfaceapp) << "Has sufficient tutorial content (" << contentVersion << ") : " << hasSufficientTutorialContent;
|
||||
qCDebug(interfaceapp) << "Tutorial complete: " << tutorialComplete.get();
|
||||
qCDebug(interfaceapp) << "Should go to tutorial: " << shouldGoToTutorial;
|
||||
|
||||
|
@ -1763,7 +1780,7 @@ void Application::initializeGL() {
|
|||
// Set up the render engine
|
||||
render::CullFunctor cullFunctor = LODManager::shouldRender;
|
||||
_renderEngine->addJob<RenderShadowTask>("RenderShadowTask", cullFunctor);
|
||||
static const QString RENDER_FORWARD = "RENDER_FORWARD";
|
||||
static const QString RENDER_FORWARD = "HIFI_RENDER_FORWARD";
|
||||
if (QProcessEnvironment::systemEnvironment().contains(RENDER_FORWARD)) {
|
||||
_renderEngine->addJob<RenderForwardTask>("RenderForwardTask", cullFunctor);
|
||||
} else {
|
||||
|
@ -1945,16 +1962,6 @@ void Application::initializeUi() {
|
|||
}
|
||||
|
||||
void Application::paintGL() {
|
||||
PROFILE_COUNTER(interfaceapp, "fps", { { "fps", _frameCounter.rate() } });
|
||||
PROFILE_COUNTER(interfaceapp, "downloads", {
|
||||
{ "current", ResourceCache::getLoadingRequests().length() },
|
||||
{ "pending", ResourceCache::getPendingRequestCount() }
|
||||
});
|
||||
PROFILE_COUNTER(interfaceapp, "processing", {
|
||||
{ "current", DependencyManager::get<StatTracker>()->getStat("Processing") },
|
||||
{ "pending", DependencyManager::get<StatTracker>()->getStat("PendingProcessing") }
|
||||
});
|
||||
|
||||
// Some plugins process message events, allowing paintGL to be called reentrantly.
|
||||
if (_inPaint || _aboutToQuit) {
|
||||
return;
|
||||
|
@ -1966,7 +1973,7 @@ void Application::paintGL() {
|
|||
_frameCount++;
|
||||
|
||||
auto lastPaintBegin = usecTimestampNow();
|
||||
PROFILE_RANGE_EX(interfaceapp, __FUNCTION__, 0xff0000ff, (uint64_t)_frameCount);
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff0000ff, (uint64_t)_frameCount);
|
||||
PerformanceTimer perfTimer("paintGL");
|
||||
|
||||
if (nullptr == _displayPlugin) {
|
||||
|
@ -2143,7 +2150,7 @@ void Application::paintGL() {
|
|||
auto finalFramebuffer = framebufferCache->getFramebuffer();
|
||||
|
||||
{
|
||||
PROFILE_RANGE(interfaceapp, "/mainRender");
|
||||
PROFILE_RANGE(render, "/mainRender");
|
||||
PerformanceTimer perfTimer("mainRender");
|
||||
renderArgs._boomOffset = boomOffset;
|
||||
// Viewport is assigned to the size of the framebuffer
|
||||
|
@ -2198,7 +2205,7 @@ void Application::paintGL() {
|
|||
frame->overlay = _applicationOverlay.getOverlayTexture();
|
||||
// deliver final scene rendering commands to the display plugin
|
||||
{
|
||||
PROFILE_RANGE(interfaceapp, "/pluginOutput");
|
||||
PROFILE_RANGE(render, "/pluginOutput");
|
||||
PerformanceTimer perfTimer("pluginOutput");
|
||||
_frameCounter.increment();
|
||||
displayPlugin->submitFrame(frame);
|
||||
|
@ -2286,7 +2293,7 @@ void Application::resizeEvent(QResizeEvent* event) {
|
|||
}
|
||||
|
||||
void Application::resizeGL() {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
if (nullptr == _displayPlugin) {
|
||||
return;
|
||||
}
|
||||
|
@ -2931,7 +2938,7 @@ void Application::maybeToggleMenuVisible(QMouseEvent* event) const {
|
|||
}
|
||||
|
||||
void Application::mouseMoveEvent(QMouseEvent* event) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(app_input_mouse, __FUNCTION__);
|
||||
|
||||
if (_aboutToQuit) {
|
||||
return;
|
||||
|
@ -3225,7 +3232,6 @@ bool Application::shouldPaint(float nsecsElapsed) {
|
|||
}
|
||||
|
||||
void Application::idle(float nsecsElapsed) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("idle");
|
||||
|
||||
// Update the deadlock watchdog
|
||||
|
@ -3241,6 +3247,18 @@ void Application::idle(float nsecsElapsed) {
|
|||
connect(offscreenUi.data(), &OffscreenUi::showDesktop, this, &Application::showDesktop);
|
||||
}
|
||||
|
||||
PROFILE_COUNTER(app, "fps", { { "fps", _frameCounter.rate() } });
|
||||
PROFILE_COUNTER(app, "downloads", {
|
||||
{ "current", ResourceCache::getLoadingRequests().length() },
|
||||
{ "pending", ResourceCache::getPendingRequestCount() }
|
||||
});
|
||||
PROFILE_COUNTER(app, "processing", {
|
||||
{ "current", DependencyManager::get<StatTracker>()->getStat("Processing") },
|
||||
{ "pending", DependencyManager::get<StatTracker>()->getStat("PendingProcessing") }
|
||||
});
|
||||
|
||||
PROFILE_RANGE(app, __FUNCTION__);
|
||||
|
||||
if (auto steamClient = PluginManager::getInstance()->getSteamClientPlugin()) {
|
||||
steamClient->runCallbacks();
|
||||
}
|
||||
|
@ -3958,7 +3976,7 @@ static bool domainLoadingInProgress = false;
|
|||
|
||||
void Application::update(float deltaTime) {
|
||||
|
||||
PROFILE_RANGE_EX(interfaceapp, __FUNCTION__, 0xffff0000, (uint64_t)_frameCount + 1);
|
||||
PROFILE_RANGE_EX(app, __FUNCTION__, 0xffff0000, (uint64_t)_frameCount + 1);
|
||||
|
||||
bool showWarnings = Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings);
|
||||
PerformanceWarning warn(showWarnings, "Application::update()");
|
||||
|
@ -3967,7 +3985,7 @@ void Application::update(float deltaTime) {
|
|||
|
||||
if (!_physicsEnabled) {
|
||||
if (!domainLoadingInProgress) {
|
||||
PROFILE_ASYNC_BEGIN(interfaceapp, "Scene Loading", "");
|
||||
PROFILE_ASYNC_BEGIN(app, "Scene Loading", "");
|
||||
domainLoadingInProgress = true;
|
||||
}
|
||||
|
||||
|
@ -4002,7 +4020,7 @@ void Application::update(float deltaTime) {
|
|||
}
|
||||
} else if (domainLoadingInProgress) {
|
||||
domainLoadingInProgress = false;
|
||||
PROFILE_ASYNC_END(interfaceapp, "Scene Loading", "");
|
||||
PROFILE_ASYNC_END(app, "Scene Loading", "");
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -4096,12 +4114,12 @@ void Application::update(float deltaTime) {
|
|||
QSharedPointer<AvatarManager> avatarManager = DependencyManager::get<AvatarManager>();
|
||||
|
||||
if (_physicsEnabled) {
|
||||
PROFILE_RANGE_EX(interfaceapp, "Physics", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation_physics, "Physics", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
|
||||
PerformanceTimer perfTimer("physics");
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "UpdateStats", 0xffffff00, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation_physics, "UpdateStats", 0xffffff00, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
|
||||
PerformanceTimer perfTimer("updateStates)");
|
||||
static VectorOfMotionStates motionStates;
|
||||
|
@ -4135,14 +4153,14 @@ void Application::update(float deltaTime) {
|
|||
});
|
||||
}
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "StepSimulation", 0xffff8000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation_physics, "StepSimulation", 0xffff8000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PerformanceTimer perfTimer("stepSimulation");
|
||||
getEntities()->getTree()->withWriteLock([&] {
|
||||
_physicsEngine->stepSimulation();
|
||||
});
|
||||
}
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "HarvestChanges", 0xffffff00, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation_physics, "HarvestChanges", 0xffffff00, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PerformanceTimer perfTimer("harvestChanges");
|
||||
if (_physicsEngine->hasOutgoingChanges()) {
|
||||
getEntities()->getTree()->withWriteLock([&] {
|
||||
|
@ -4184,20 +4202,20 @@ void Application::update(float deltaTime) {
|
|||
_avatarSimCounter.increment();
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "OtherAvatars", 0xffff00ff, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation, "OtherAvatars", 0xffff00ff, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
avatarManager->updateOtherAvatars(deltaTime);
|
||||
}
|
||||
|
||||
qApp->updateMyAvatarLookAtPosition();
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "MyAvatar", 0xffff00ff, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(simulation, "MyAvatar", 0xffff00ff, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
avatarManager->updateMyAvatar(deltaTime);
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "Overlays", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(app, "Overlays", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PerformanceTimer perfTimer("overlays");
|
||||
_overlays.update(deltaTime);
|
||||
}
|
||||
|
@ -4217,7 +4235,7 @@ void Application::update(float deltaTime) {
|
|||
|
||||
// Update my voxel servers with my current voxel query...
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "QueryOctree", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
PROFILE_RANGE_EX(app, "QueryOctree", 0xffff0000, (uint64_t)getActiveDisplayPlugin()->presentCount());
|
||||
QMutexLocker viewLocker(&_viewMutex);
|
||||
PerformanceTimer perfTimer("queryOctree");
|
||||
quint64 sinceLastQuery = now - _lastQueriedTime;
|
||||
|
@ -4257,7 +4275,7 @@ void Application::update(float deltaTime) {
|
|||
avatarManager->postUpdate(deltaTime);
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(interfaceapp, "PreRenderLambdas", 0xffff0000, (uint64_t)0);
|
||||
PROFILE_RANGE_EX(app, "PreRenderLambdas", 0xffff0000, (uint64_t)0);
|
||||
|
||||
std::unique_lock<std::mutex> guard(_postUpdateLambdasLock);
|
||||
for (auto& iter : _postUpdateLambdas) {
|
||||
|
@ -4534,8 +4552,6 @@ QRect Application::getDesirableApplicationGeometry() const {
|
|||
// or the "myCamera".
|
||||
//
|
||||
void Application::loadViewFrustum(Camera& camera, ViewFrustum& viewFrustum) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("loadViewFrustum");
|
||||
// We will use these below, from either the camera or head vectors calculated above
|
||||
viewFrustum.setProjection(camera.getProjection());
|
||||
|
||||
|
@ -4711,7 +4727,7 @@ void Application::displaySide(RenderArgs* renderArgs, Camera& theCamera, bool se
|
|||
myAvatar->preDisplaySide(renderArgs);
|
||||
|
||||
activeRenderingThread = QThread::currentThread();
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("display");
|
||||
PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "Application::displaySide()");
|
||||
|
||||
|
|
|
@ -49,12 +49,17 @@ glm::vec2 HMDScriptingInterface::overlayToSpherical(const glm::vec2 & position)
|
|||
return qApp->getApplicationCompositor().overlayToSpherical(position);
|
||||
}
|
||||
|
||||
bool HMDScriptingInterface::isHMDAvailable() {
|
||||
return PluginUtils::isHMDAvailable();
|
||||
bool HMDScriptingInterface::isHMDAvailable(const QString& name) {
|
||||
return PluginUtils::isHMDAvailable(name);
|
||||
}
|
||||
|
||||
bool HMDScriptingInterface::isHandControllerAvailable() {
|
||||
return PluginUtils::isHandControllerAvailable();
|
||||
bool HMDScriptingInterface::isHandControllerAvailable(const QString& name) {
|
||||
return PluginUtils::isHandControllerAvailable(name);
|
||||
}
|
||||
|
||||
|
||||
bool HMDScriptingInterface::isSubdeviceContainingNameAvailable(const QString& name) {
|
||||
return PluginUtils::isSubdeviceContainingNameAvailable(name);
|
||||
}
|
||||
|
||||
void HMDScriptingInterface::requestShowHandControllers() {
|
||||
|
|
|
@ -38,8 +38,9 @@ public:
|
|||
Q_INVOKABLE QString preferredAudioInput() const;
|
||||
Q_INVOKABLE QString preferredAudioOutput() const;
|
||||
|
||||
Q_INVOKABLE bool isHMDAvailable();
|
||||
Q_INVOKABLE bool isHandControllerAvailable();
|
||||
Q_INVOKABLE bool isHMDAvailable(const QString& name = "");
|
||||
Q_INVOKABLE bool isHandControllerAvailable(const QString& name = "");
|
||||
Q_INVOKABLE bool isSubdeviceContainingNameAvailable(const QString& name);
|
||||
|
||||
Q_INVOKABLE void requestShowHandControllers();
|
||||
Q_INVOKABLE void requestHideHandControllers();
|
||||
|
|
|
@ -57,7 +57,7 @@ ApplicationOverlay::~ApplicationOverlay() {
|
|||
|
||||
// Renders the overlays either to a texture or to the screen
|
||||
void ApplicationOverlay::renderOverlay(RenderArgs* renderArgs) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
PerformanceWarning warn(Menu::getInstance()->isOptionChecked(MenuOption::PipelineWarnings), "ApplicationOverlay::displayOverlay()");
|
||||
|
||||
buildFramebufferObject();
|
||||
|
@ -96,7 +96,7 @@ void ApplicationOverlay::renderOverlay(RenderArgs* renderArgs) {
|
|||
}
|
||||
|
||||
void ApplicationOverlay::renderQmlUi(RenderArgs* renderArgs) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(app, __FUNCTION__);
|
||||
|
||||
if (!_uiTexture) {
|
||||
_uiTexture = gpu::TexturePointer(gpu::Texture::createExternal2D(OffscreenQmlSurface::getDiscardLambda()));
|
||||
|
@ -124,7 +124,7 @@ void ApplicationOverlay::renderQmlUi(RenderArgs* renderArgs) {
|
|||
}
|
||||
|
||||
void ApplicationOverlay::renderAudioScope(RenderArgs* renderArgs) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(app, __FUNCTION__);
|
||||
|
||||
gpu::Batch& batch = *renderArgs->_batch;
|
||||
auto geometryCache = DependencyManager::get<GeometryCache>();
|
||||
|
@ -143,7 +143,7 @@ void ApplicationOverlay::renderAudioScope(RenderArgs* renderArgs) {
|
|||
}
|
||||
|
||||
void ApplicationOverlay::renderOverlays(RenderArgs* renderArgs) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(app, __FUNCTION__);
|
||||
|
||||
gpu::Batch& batch = *renderArgs->_batch;
|
||||
auto geometryCache = DependencyManager::get<GeometryCache>();
|
||||
|
@ -262,7 +262,7 @@ static const auto DEFAULT_SAMPLER = gpu::Sampler(gpu::Sampler::FILTER_MIN_MAG_LI
|
|||
static const auto DEPTH_FORMAT = gpu::Element(gpu::SCALAR, gpu::FLOAT, gpu::DEPTH);
|
||||
|
||||
void ApplicationOverlay::buildFramebufferObject() {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(app, __FUNCTION__);
|
||||
|
||||
auto uiSize = qApp->getUiSize();
|
||||
if (!_overlayFramebuffer || uiSize != _overlayFramebuffer->getSize()) {
|
||||
|
|
|
@ -37,6 +37,7 @@
|
|||
#include "Web3DOverlay.h"
|
||||
#include <QtQuick/QQuickWindow>
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_render_overlays, "trace.render.overlays")
|
||||
|
||||
Overlays::Overlays() :
|
||||
_nextOverlayID(1) {}
|
||||
|
@ -102,7 +103,7 @@ void Overlays::cleanupOverlaysToDelete() {
|
|||
}
|
||||
|
||||
void Overlays::renderHUD(RenderArgs* renderArgs) {
|
||||
PROFILE_RANGE(interfaceapp, __FUNCTION__);
|
||||
PROFILE_RANGE(render_overlays, __FUNCTION__);
|
||||
QReadLocker lock(&_lock);
|
||||
gpu::Batch& batch = *renderArgs->_batch;
|
||||
|
||||
|
|
|
@ -394,7 +394,7 @@ const AnimPoseVec& AnimInverseKinematics::overlay(const AnimVariantMap& animVars
|
|||
loadPoses(underPoses);
|
||||
} else {
|
||||
|
||||
PROFILE_RANGE_EX(animation, "ik/relax", 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, "ik/relax", 0xffff00ff, 0);
|
||||
|
||||
// relax toward underPoses
|
||||
// HACK: this relaxation needs to be constant per-frame rather than per-realtime
|
||||
|
@ -433,7 +433,7 @@ const AnimPoseVec& AnimInverseKinematics::overlay(const AnimVariantMap& animVars
|
|||
// build a list of targets from _targetVarVec
|
||||
std::vector<IKTarget> targets;
|
||||
{
|
||||
PROFILE_RANGE_EX(animation, "ik/computeTargets", 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, "ik/computeTargets", 0xffff00ff, 0);
|
||||
computeTargets(animVars, targets, underPoses);
|
||||
}
|
||||
|
||||
|
@ -450,7 +450,7 @@ const AnimPoseVec& AnimInverseKinematics::overlay(const AnimVariantMap& animVars
|
|||
} else {
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(animation, "ik/shiftHips", 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, "ik/shiftHips", 0xffff00ff, 0);
|
||||
|
||||
// shift hips according to the _hipsOffset from the previous frame
|
||||
float offsetLength = glm::length(_hipsOffset);
|
||||
|
@ -476,12 +476,12 @@ const AnimPoseVec& AnimInverseKinematics::overlay(const AnimVariantMap& animVars
|
|||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(animation, "ik/ccd", 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, "ik/ccd", 0xffff00ff, 0);
|
||||
solveWithCyclicCoordinateDescent(targets);
|
||||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(animation, "ik/measureHipsOffset", 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, "ik/measureHipsOffset", 0xffff00ff, 0);
|
||||
|
||||
// measure new _hipsOffset for next frame
|
||||
// by looking for discrepancies between where a targeted endEffector is
|
||||
|
|
|
@ -55,7 +55,7 @@ void AnimationReader::run() {
|
|||
DependencyManager::get<StatTracker>()->decrementStat("PendingProcessing");
|
||||
CounterStat counter("Processing");
|
||||
|
||||
PROFILE_RANGE_EX(animation, __FUNCTION__, 0xFF00FF00, 0, { { "url", _url.toString() } });
|
||||
PROFILE_RANGE_EX(resource_parse, __FUNCTION__, 0xFF00FF00, 0, { { "url", _url.toString() } });
|
||||
auto originalPriority = QThread::currentThread()->priority();
|
||||
if (originalPriority == QThread::InheritPriority) {
|
||||
originalPriority = QThread::NormalPriority;
|
||||
|
|
|
@ -883,7 +883,7 @@ void Rig::updateAnimationStateHandlers() { // called on avatar update thread (wh
|
|||
|
||||
void Rig::updateAnimations(float deltaTime, glm::mat4 rootTransform) {
|
||||
|
||||
PROFILE_RANGE_EX(animation, __FUNCTION__, 0xffff00ff, 0);
|
||||
PROFILE_RANGE_EX(simulation_animation, __FUNCTION__, 0xffff00ff, 0);
|
||||
|
||||
setModelOffset(rootTransform);
|
||||
|
||||
|
|
|
@ -1135,8 +1135,9 @@ void AudioClient::mixLocalAudioInjectors(float* mixBuffer) {
|
|||
} else if (injector->isStereo()) {
|
||||
|
||||
// stereo gets directly mixed into mixBuffer
|
||||
float gain = injector->getVolume();
|
||||
for (int i = 0; i < AudioConstants::NETWORK_FRAME_SAMPLES_STEREO; i++) {
|
||||
mixBuffer[i] += (float)_scratchBuffer[i] * (1/32768.0f);
|
||||
mixBuffer[i] += (float)_scratchBuffer[i] * (1/32768.0f) * gain;
|
||||
}
|
||||
|
||||
} else {
|
||||
|
|
|
@ -166,7 +166,6 @@ bool AudioInjector::injectLocally() {
|
|||
|
||||
_localBuffer->open(QIODevice::ReadOnly);
|
||||
_localBuffer->setShouldLoop(_options.loop);
|
||||
_localBuffer->setVolume(_options.volume);
|
||||
|
||||
// give our current send position to the local buffer
|
||||
_localBuffer->setCurrentOffset(_currentSendOffset);
|
||||
|
|
|
@ -63,7 +63,7 @@ public:
|
|||
AudioFOA& getLocalFOA() { return _localFOA; }
|
||||
|
||||
bool isLocalOnly() const { return _options.localOnly; }
|
||||
float getVolume() const { return _options.volume; }
|
||||
float getVolume() const { return glm::clamp(_options.volume, 0.0f, 1.0f); }
|
||||
glm::vec3 getPosition() const { return _options.position; }
|
||||
glm::quat getOrientation() const { return _options.orientation; }
|
||||
bool isStereo() const { return _options.stereo; }
|
||||
|
|
|
@ -16,8 +16,7 @@ AudioInjectorLocalBuffer::AudioInjectorLocalBuffer(const QByteArray& rawAudioArr
|
|||
_rawAudioArray(rawAudioArray),
|
||||
_shouldLoop(false),
|
||||
_isStopped(false),
|
||||
_currentOffset(0),
|
||||
_volume(1.0f)
|
||||
_currentOffset(0)
|
||||
{
|
||||
|
||||
}
|
||||
|
@ -36,17 +35,6 @@ bool AudioInjectorLocalBuffer::seek(qint64 pos) {
|
|||
}
|
||||
}
|
||||
|
||||
void copy(char* to, char* from, int size, qreal factor) {
|
||||
int16_t* toArray = (int16_t*) to;
|
||||
int16_t* fromArray = (int16_t*) from;
|
||||
int sampleSize = size / sizeof(int16_t);
|
||||
|
||||
for (int i = 0; i < sampleSize; i++) {
|
||||
*toArray = factor * (*fromArray);
|
||||
toArray++;
|
||||
fromArray++;
|
||||
}
|
||||
}
|
||||
|
||||
qint64 AudioInjectorLocalBuffer::readData(char* data, qint64 maxSize) {
|
||||
if (!_isStopped) {
|
||||
|
@ -60,7 +48,7 @@ qint64 AudioInjectorLocalBuffer::readData(char* data, qint64 maxSize) {
|
|||
bytesRead = bytesToEnd;
|
||||
}
|
||||
|
||||
copy(data, _rawAudioArray.data() + _currentOffset, bytesRead, _volume);
|
||||
memcpy(data, _rawAudioArray.data() + _currentOffset, bytesRead);
|
||||
|
||||
// now check if we are supposed to loop and if we can copy more from the beginning
|
||||
if (_shouldLoop && maxSize != bytesRead) {
|
||||
|
@ -88,7 +76,7 @@ qint64 AudioInjectorLocalBuffer::recursiveReadFromFront(char* data, qint64 maxSi
|
|||
}
|
||||
|
||||
// copy that amount
|
||||
copy(data, _rawAudioArray.data(), bytesRead, _volume);
|
||||
memcpy(data, _rawAudioArray.data(), bytesRead);
|
||||
|
||||
// check if we need to call ourselves again and pull from the front again
|
||||
if (bytesRead < maxSize) {
|
||||
|
@ -97,4 +85,4 @@ qint64 AudioInjectorLocalBuffer::recursiveReadFromFront(char* data, qint64 maxSi
|
|||
_currentOffset = bytesRead;
|
||||
return bytesRead;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,7 +30,6 @@ public:
|
|||
|
||||
void setShouldLoop(bool shouldLoop) { _shouldLoop = shouldLoop; }
|
||||
void setCurrentOffset(int currentOffset) { _currentOffset = currentOffset; }
|
||||
void setVolume(float volume) { _volume = glm::clamp(volume, 0.0f, 1.0f); }
|
||||
|
||||
private:
|
||||
qint64 recursiveReadFromFront(char* data, qint64 maxSize);
|
||||
|
@ -40,7 +39,6 @@ private:
|
|||
bool _isStopped;
|
||||
|
||||
int _currentOffset;
|
||||
float _volume;
|
||||
};
|
||||
|
||||
#endif // hifi_AudioInjectorLocalBuffer_h
|
||||
|
|
|
@ -129,7 +129,7 @@ public:
|
|||
_context->makeCurrent();
|
||||
while (!_shutdown) {
|
||||
if (_pendingMainThreadOperation) {
|
||||
PROFILE_RANGE(displayPlugins, "MainThreadOp")
|
||||
PROFILE_RANGE(render, "MainThreadOp")
|
||||
{
|
||||
Lock lock(_mutex);
|
||||
_context->doneCurrent();
|
||||
|
@ -203,7 +203,7 @@ public:
|
|||
// Execute the frame and present it to the display device.
|
||||
_context->makeCurrent();
|
||||
{
|
||||
PROFILE_RANGE(displayPlugins, "PluginPresent")
|
||||
PROFILE_RANGE(render, "PluginPresent")
|
||||
currentPlugin->present();
|
||||
CHECK_GL_ERROR();
|
||||
}
|
||||
|
@ -560,22 +560,22 @@ void OpenGLDisplayPlugin::compositeLayers() {
|
|||
updateCompositeFramebuffer();
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "compositeScene", 0xff0077ff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "compositeScene", 0xff0077ff, (uint64_t)presentCount())
|
||||
compositeScene();
|
||||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "compositeOverlay", 0xff0077ff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "compositeOverlay", 0xff0077ff, (uint64_t)presentCount())
|
||||
compositeOverlay();
|
||||
}
|
||||
auto compositorHelper = DependencyManager::get<CompositorHelper>();
|
||||
if (compositorHelper->getReticleVisible()) {
|
||||
PROFILE_RANGE_EX(displayPlugins, "compositePointer", 0xff0077ff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "compositePointer", 0xff0077ff, (uint64_t)presentCount())
|
||||
compositePointer();
|
||||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "compositeExtra", 0xff0077ff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "compositeExtra", 0xff0077ff, (uint64_t)presentCount())
|
||||
compositeExtra();
|
||||
}
|
||||
}
|
||||
|
@ -595,12 +595,12 @@ void OpenGLDisplayPlugin::internalPresent() {
|
|||
}
|
||||
|
||||
void OpenGLDisplayPlugin::present() {
|
||||
PROFILE_RANGE_EX(displayPlugins, __FUNCTION__, 0xffffff00, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xffffff00, (uint64_t)presentCount())
|
||||
updateFrameData();
|
||||
incrementPresentCount();
|
||||
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "recycle", 0xff00ff00, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "recycle", 0xff00ff00, (uint64_t)presentCount())
|
||||
_gpuContext->recycle();
|
||||
}
|
||||
|
||||
|
@ -614,19 +614,19 @@ void OpenGLDisplayPlugin::present() {
|
|||
_lastFrame = _currentFrame.get();
|
||||
});
|
||||
// Execute the frame rendering commands
|
||||
PROFILE_RANGE_EX(displayPlugins, "execute", 0xff00ff00, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "execute", 0xff00ff00, (uint64_t)presentCount())
|
||||
_gpuContext->executeFrame(_currentFrame);
|
||||
}
|
||||
|
||||
// Write all layers to a local framebuffer
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "composite", 0xff00ffff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "composite", 0xff00ffff, (uint64_t)presentCount())
|
||||
compositeLayers();
|
||||
}
|
||||
|
||||
// Take the composite framebuffer and send it to the output device
|
||||
{
|
||||
PROFILE_RANGE_EX(displayPlugins, "internalPresent", 0xff00ffff, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, "internalPresent", 0xff00ffff, (uint64_t)presentCount())
|
||||
internalPresent();
|
||||
}
|
||||
|
||||
|
|
|
@ -206,7 +206,7 @@ float HmdDisplayPlugin::getLeftCenterPixel() const {
|
|||
}
|
||||
|
||||
void HmdDisplayPlugin::internalPresent() {
|
||||
PROFILE_RANGE_EX(displayPlugins, __FUNCTION__, 0xff00ff00, (uint64_t)presentCount())
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff00ff00, (uint64_t)presentCount())
|
||||
|
||||
// Composite together the scene, overlay and mouse cursor
|
||||
hmdPresent();
|
||||
|
|
|
@ -211,7 +211,7 @@ namespace render {
|
|||
template <> void payloadRender(const RenderableModelEntityItemMeta::Pointer& payload, RenderArgs* args) {
|
||||
if (args) {
|
||||
if (payload && payload->entity) {
|
||||
PROFILE_RANGE(renderlogging, "MetaModelRender");
|
||||
PROFILE_RANGE(render, "MetaModelRender");
|
||||
payload->entity->render(args);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -321,7 +321,7 @@ FBXNode parseTextFBXNode(Tokenizer& tokenizer) {
|
|||
}
|
||||
|
||||
FBXNode FBXReader::parseFBX(QIODevice* device) {
|
||||
PROFILE_RANGE_EX(modelformat, __FUNCTION__, 0xff0000ff, device);
|
||||
PROFILE_RANGE_EX(resource_parse, __FUNCTION__, 0xff0000ff, device);
|
||||
// verify the prolog
|
||||
const QByteArray BINARY_PROLOG = "Kaydara FBX Binary ";
|
||||
if (device->peek(BINARY_PROLOG.size()) != BINARY_PROLOG) {
|
||||
|
|
|
@ -420,7 +420,7 @@ done:
|
|||
|
||||
|
||||
FBXGeometry* OBJReader::readOBJ(QByteArray& model, const QVariantHash& mapping, const QUrl& url) {
|
||||
PROFILE_RANGE_EX(modelformat, __FUNCTION__, 0xffff0000, nullptr);
|
||||
PROFILE_RANGE_EX(resource_parse, __FUNCTION__, 0xffff0000, nullptr);
|
||||
QBuffer buffer { &model };
|
||||
buffer.open(QIODevice::ReadOnly);
|
||||
|
||||
|
|
|
@ -38,6 +38,9 @@
|
|||
#include "GLLogging.h"
|
||||
#include "Context.h"
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_render_qml, "trace.render.qml")
|
||||
Q_LOGGING_CATEGORY(trace_render_qml_gl, "trace.render.qml.gl")
|
||||
|
||||
struct TextureSet {
|
||||
// The number of surfaces with this size
|
||||
size_t count { 0 };
|
||||
|
@ -276,6 +279,7 @@ void OffscreenQmlSurface::render() {
|
|||
return;
|
||||
}
|
||||
|
||||
PROFILE_RANGE(render_qml_gl, __FUNCTION__)
|
||||
_canvas->makeCurrent();
|
||||
|
||||
_renderControl->sync();
|
||||
|
@ -284,7 +288,6 @@ void OffscreenQmlSurface::render() {
|
|||
GLuint texture = offscreenTextures.getNextTexture(_size);
|
||||
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, _fbo);
|
||||
glFramebufferTexture(GL_DRAW_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, texture, 0);
|
||||
PROFILE_RANGE(glLogging, "qml_render->rendercontrol")
|
||||
_renderControl->render();
|
||||
glBindFramebuffer(GL_DRAW_FRAMEBUFFER, 0);
|
||||
glBindTexture(GL_TEXTURE_2D, texture);
|
||||
|
@ -617,12 +620,12 @@ void OffscreenQmlSurface::updateQuick() {
|
|||
}
|
||||
|
||||
if (_polish) {
|
||||
PROFILE_RANGE(render_qml, "OffscreenQML polish")
|
||||
_renderControl->polishItems();
|
||||
_polish = false;
|
||||
}
|
||||
|
||||
if (_render) {
|
||||
PROFILE_RANGE(glLogging, __FUNCTION__);
|
||||
render();
|
||||
_render = false;
|
||||
}
|
||||
|
|
|
@ -200,7 +200,7 @@ void GLBackend::renderPassTransfer(const Batch& batch) {
|
|||
|
||||
_inRenderTransferPass = true;
|
||||
{ // Sync all the buffers
|
||||
PROFILE_RANGE(gpugllogging, "syncGPUBuffer");
|
||||
PROFILE_RANGE(render_gpu_gl, "syncGPUBuffer");
|
||||
|
||||
for (auto& cached : batch._buffers._items) {
|
||||
if (cached._data) {
|
||||
|
@ -210,7 +210,7 @@ void GLBackend::renderPassTransfer(const Batch& batch) {
|
|||
}
|
||||
|
||||
{ // Sync all the buffers
|
||||
PROFILE_RANGE(gpugllogging, "syncCPUTransform");
|
||||
PROFILE_RANGE(render_gpu_gl, "syncCPUTransform");
|
||||
_transform._cameras.clear();
|
||||
_transform._cameraOffsets.clear();
|
||||
|
||||
|
@ -242,7 +242,7 @@ void GLBackend::renderPassTransfer(const Batch& batch) {
|
|||
}
|
||||
|
||||
{ // Sync the transform buffers
|
||||
PROFILE_RANGE(gpugllogging, "syncGPUTransform");
|
||||
PROFILE_RANGE(render_gpu_gl, "syncGPUTransform");
|
||||
transferTransformState(batch);
|
||||
}
|
||||
|
||||
|
@ -304,7 +304,7 @@ void GLBackend::render(const Batch& batch) {
|
|||
}
|
||||
|
||||
{
|
||||
PROFILE_RANGE(gpugllogging, "Transfer");
|
||||
PROFILE_RANGE(render_gpu_gl, "Transfer");
|
||||
renderPassTransfer(batch);
|
||||
}
|
||||
|
||||
|
@ -314,7 +314,7 @@ void GLBackend::render(const Batch& batch) {
|
|||
}
|
||||
#endif
|
||||
{
|
||||
PROFILE_RANGE(gpugllogging, _stereo._enable ? "Render Stereo" : "Render");
|
||||
PROFILE_RANGE(render_gpu_gl, _stereo._enable ? "Render Stereo" : "Render");
|
||||
renderPassDraw(batch);
|
||||
}
|
||||
#ifdef GPU_STEREO_DRAWCALL_INSTANCED
|
||||
|
|
|
@ -28,7 +28,7 @@ void GLBackend::do_beginQuery(const Batch& batch, size_t paramOffset) {
|
|||
auto query = batch._queries.get(batch._params[paramOffset]._uint);
|
||||
GLQuery* glquery = syncGPUObject(*query);
|
||||
if (glquery) {
|
||||
PROFILE_RANGE_BEGIN(gpugllogging, glquery->_profileRangeId, query->getName().c_str(), 0xFFFF7F00);
|
||||
PROFILE_RANGE_BEGIN(render_gpu_gl, glquery->_profileRangeId, query->getName().c_str(), 0xFFFF7F00);
|
||||
|
||||
++_queryStage._rangeQueryDepth;
|
||||
glGetInteger64v(GL_TIMESTAMP, (GLint64*)&glquery->_batchElapsedTime);
|
||||
|
@ -62,7 +62,7 @@ void GLBackend::do_endQuery(const Batch& batch, size_t paramOffset) {
|
|||
glGetInteger64v(GL_TIMESTAMP, &now);
|
||||
glquery->_batchElapsedTime = now - glquery->_batchElapsedTime;
|
||||
|
||||
PROFILE_RANGE_END(gpugllogging, glquery->_profileRangeId);
|
||||
PROFILE_RANGE_END(render_gpu_gl, glquery->_profileRangeId);
|
||||
|
||||
(void)CHECK_GL_ERROR();
|
||||
}
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
#include <fstream>
|
||||
|
||||
Q_LOGGING_CATEGORY(gpugllogging, "hifi.gpu.gl")
|
||||
Q_LOGGING_CATEGORY(trace_render_gpu_gl, "trace.render.gpu.gl")
|
||||
|
||||
namespace gpu { namespace gl {
|
||||
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
#include <QLoggingCategory>
|
||||
|
||||
Q_DECLARE_LOGGING_CATEGORY(gpugllogging)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_render_gpu_gl)
|
||||
|
||||
namespace gpu { namespace gl {
|
||||
|
||||
|
|
|
@ -122,7 +122,7 @@ void GL41Texture::transferMip(uint16_t mipLevel, uint8_t face) const {
|
|||
}
|
||||
|
||||
void GL41Texture::startTransfer() {
|
||||
PROFILE_RANGE(gpugllogging, __FUNCTION__);
|
||||
PROFILE_RANGE(render_gpu_gl, __FUNCTION__);
|
||||
Parent::startTransfer();
|
||||
|
||||
glBindTexture(_target, _id);
|
||||
|
|
|
@ -759,7 +759,7 @@ bool sphericalHarmonicsFromTexture(const gpu::Texture& cubeTexture, std::vector<
|
|||
return false;
|
||||
}
|
||||
|
||||
PROFILE_RANGE(gpulogging, "sphericalHarmonicsFromTexture");
|
||||
PROFILE_RANGE(render_gpu, "sphericalHarmonicsFromTexture");
|
||||
|
||||
const uint sqOrder = order*order;
|
||||
|
||||
|
@ -792,7 +792,7 @@ bool sphericalHarmonicsFromTexture(const gpu::Texture& cubeTexture, std::vector<
|
|||
|
||||
// for each face of cube texture
|
||||
for(int face=0; face < gpu::Texture::NUM_CUBE_FACES; face++) {
|
||||
PROFILE_RANGE(gpulogging, "ProcessFace");
|
||||
PROFILE_RANGE(render_gpu, "ProcessFace");
|
||||
|
||||
auto numComponents = cubeTexture.accessStoredMipFace(0,face)->getFormat().getScalarCount();
|
||||
auto data = cubeTexture.accessStoredMipFace(0,face)->readData();
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <Trace.h>
|
||||
#include <StatTracker.h>
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_resource_parse_geometry, "trace.resource.parse.geometry")
|
||||
|
||||
class GeometryReader;
|
||||
|
||||
class GeometryExtra {
|
||||
|
@ -54,7 +56,7 @@ private:
|
|||
};
|
||||
|
||||
void GeometryMappingResource::downloadFinished(const QByteArray& data) {
|
||||
PROFILE_ASYNC_BEGIN(modelnetworking, "GeometryMappingResource::downloadFinished", _url.toString(),
|
||||
PROFILE_ASYNC_BEGIN(resource_parse_geometry, "GeometryMappingResource::downloadFinished", _url.toString(),
|
||||
{ { "url", _url.toString() } });
|
||||
|
||||
auto mapping = FSTReader::readMapping(data);
|
||||
|
@ -120,7 +122,7 @@ void GeometryMappingResource::onGeometryMappingLoaded(bool success) {
|
|||
disconnect(_connection); // FIXME Should not have to do this
|
||||
}
|
||||
|
||||
PROFILE_ASYNC_END(modelnetworking, "GeometryMappingResource::downloadFinished", _url.toString());
|
||||
PROFILE_ASYNC_END(resource_parse_geometry, "GeometryMappingResource::downloadFinished", _url.toString());
|
||||
finishedLoading(success);
|
||||
}
|
||||
|
||||
|
@ -145,7 +147,7 @@ private:
|
|||
void GeometryReader::run() {
|
||||
DependencyManager::get<StatTracker>()->decrementStat("PendingProcessing");
|
||||
CounterStat counter("Processing");
|
||||
PROFILE_RANGE_EX(modelnetworking, "GeometryReader::run", 0xFF00FF00, 0, { { "url", _url.toString() } });
|
||||
PROFILE_RANGE_EX(resource_parse_geometry, "GeometryReader::run", 0xFF00FF00, 0, { { "url", _url.toString() } });
|
||||
auto originalPriority = QThread::currentThread()->priority();
|
||||
if (originalPriority == QThread::InheritPriority) {
|
||||
originalPriority = QThread::NormalPriority;
|
||||
|
|
|
@ -36,6 +36,8 @@
|
|||
#include <Trace.h>
|
||||
#include <StatTracker.h>
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_resource_parse_image, "trace.resource.parse.image")
|
||||
|
||||
TextureCache::TextureCache() {
|
||||
setUnusedResourceCacheSize(0);
|
||||
setObjectName("TextureCache");
|
||||
|
@ -349,7 +351,7 @@ void ImageReader::run() {
|
|||
|
||||
CounterStat counter("Processing");
|
||||
|
||||
PROFILE_RANGE_EX(modelnetworking, __FUNCTION__, 0xffff0000, 0, { { "url", _url.toString() } });
|
||||
PROFILE_RANGE_EX(resource_parse_image, __FUNCTION__, 0xffff0000, 0, { { "url", _url.toString() } });
|
||||
auto originalPriority = QThread::currentThread()->priority();
|
||||
if (originalPriority == QThread::InheritPriority) {
|
||||
originalPriority = QThread::NormalPriority;
|
||||
|
@ -395,7 +397,7 @@ void ImageReader::run() {
|
|||
|
||||
auto url = _url.toString().toStdString();
|
||||
|
||||
PROFILE_RANGE_EX(modelnetworking, __FUNCTION__, 0xffffff00, 0);
|
||||
PROFILE_RANGE_EX(resource_parse_image, __FUNCTION__, 0xffffff00, 0);
|
||||
texture.reset(resource.dynamicCast<NetworkTexture>()->getTextureLoader()(image, url));
|
||||
}
|
||||
|
||||
|
|
|
@ -746,7 +746,7 @@ const CubeLayout CubeLayout::CUBEMAP_LAYOUTS[] = {
|
|||
const int CubeLayout::NUM_CUBEMAP_LAYOUTS = sizeof(CubeLayout::CUBEMAP_LAYOUTS) / sizeof(CubeLayout);
|
||||
|
||||
gpu::Texture* TextureUsage::processCubeTextureColorFromImage(const QImage& srcImage, const std::string& srcImageName, bool isLinear, bool doCompress, bool generateMips, bool generateIrradiance) {
|
||||
PROFILE_RANGE(modelLog, "processCubeTextureColorFromImage");
|
||||
PROFILE_RANGE(resource_parse, "processCubeTextureColorFromImage");
|
||||
|
||||
gpu::Texture* theTexture = nullptr;
|
||||
if ((srcImage.width() > 0) && (srcImage.height() > 0)) {
|
||||
|
@ -805,13 +805,13 @@ gpu::Texture* TextureUsage::processCubeTextureColorFromImage(const QImage& srcIm
|
|||
}
|
||||
|
||||
if (generateMips) {
|
||||
PROFILE_RANGE(modelLog, "generateMips");
|
||||
PROFILE_RANGE(resource_parse, "generateMips");
|
||||
theTexture->autoGenerateMips(-1);
|
||||
}
|
||||
|
||||
// Generate irradiance while we are at it
|
||||
if (generateIrradiance) {
|
||||
PROFILE_RANGE(modelLog, "generateIrradiance");
|
||||
PROFILE_RANGE(resource_parse, "generateIrradiance");
|
||||
theTexture->generateIrradiance();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -650,12 +650,12 @@ void Resource::reinsert() {
|
|||
|
||||
void Resource::makeRequest() {
|
||||
if (_request) {
|
||||
PROFILE_ASYNC_END(resourceLog, "Resource:" + getType(), QString::number(_requestID));
|
||||
PROFILE_ASYNC_END(resource, "Resource:" + getType(), QString::number(_requestID));
|
||||
_request->disconnect();
|
||||
_request->deleteLater();
|
||||
}
|
||||
|
||||
PROFILE_ASYNC_BEGIN(resourceLog, "Resource:" + getType(), QString::number(_requestID), { { "url", _url.toString() }, { "activeURL", _activeUrl.toString() } });
|
||||
PROFILE_ASYNC_BEGIN(resource, "Resource:" + getType(), QString::number(_requestID), { { "url", _url.toString() }, { "activeURL", _activeUrl.toString() } });
|
||||
|
||||
_request = ResourceManager::createResourceRequest(this, _activeUrl);
|
||||
|
||||
|
@ -663,7 +663,7 @@ void Resource::makeRequest() {
|
|||
qCDebug(networking).noquote() << "Failed to get request for" << _url.toDisplayString();
|
||||
ResourceCache::requestCompleted(_self);
|
||||
finishedLoading(false);
|
||||
PROFILE_ASYNC_END(resourceLog, "Resource:" + getType(), QString::number(_requestID));
|
||||
PROFILE_ASYNC_END(resource, "Resource:" + getType(), QString::number(_requestID));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -688,7 +688,7 @@ void Resource::handleDownloadProgress(uint64_t bytesReceived, uint64_t bytesTota
|
|||
void Resource::handleReplyFinished() {
|
||||
Q_ASSERT_X(_request, "Resource::handleReplyFinished", "Request should not be null while in handleReplyFinished");
|
||||
|
||||
PROFILE_ASYNC_END(resourceLog, "Resource:" + getType(), QString::number(_requestID), {
|
||||
PROFILE_ASYNC_END(resource, "Resource:" + getType(), QString::number(_requestID), {
|
||||
{ "from_cache", _request->loadedFromCache() },
|
||||
{ "size_mb", _bytesTotal / 1000000.0 }
|
||||
});
|
||||
|
|
|
@ -25,14 +25,15 @@ void UserActivityLoggerScriptingInterface::toggledAway(bool isAway) {
|
|||
}
|
||||
|
||||
void UserActivityLoggerScriptingInterface::tutorialProgress( QString stepName, int stepNumber, float secondsToComplete,
|
||||
float tutorialElapsedTime, QString tutorialRunID, int tutorialVersion) {
|
||||
float tutorialElapsedTime, QString tutorialRunID, int tutorialVersion, QString controllerType) {
|
||||
logAction("tutorial_progress", {
|
||||
{ "tutorial_run_id", tutorialRunID },
|
||||
{ "tutorial_version", tutorialVersion },
|
||||
{ "step", stepName },
|
||||
{ "step_number", stepNumber },
|
||||
{ "seconds_to_complete", secondsToComplete },
|
||||
{ "tutorial_elapsed_seconds", tutorialElapsedTime }
|
||||
{ "tutorial_elapsed_seconds", tutorialElapsedTime },
|
||||
{ "controller_type", controllerType }
|
||||
});
|
||||
|
||||
}
|
||||
|
|
|
@ -24,7 +24,7 @@ public:
|
|||
Q_INVOKABLE void openedMarketplace();
|
||||
Q_INVOKABLE void toggledAway(bool isAway);
|
||||
Q_INVOKABLE void tutorialProgress(QString stepName, int stepNumber, float secondsToComplete,
|
||||
float tutorialElapsedTime, QString tutorialRunID = "", int tutorialVersion = 0);
|
||||
float tutorialElapsedTime, QString tutorialRunID = "", int tutorialVersion = 0, QString controllerType = "");
|
||||
|
||||
private:
|
||||
void logAction(QString action, QJsonObject details = {});
|
||||
|
|
|
@ -86,7 +86,7 @@ SendQueue::SendQueue(Socket* socket, HifiSockAddr dest) :
|
|||
_socket(socket),
|
||||
_destination(dest)
|
||||
{
|
||||
PROFILE_ASYNC_BEGIN(networking, "SendQueue", _destination.toString());
|
||||
PROFILE_ASYNC_BEGIN(network, "SendQueue", _destination.toString());
|
||||
|
||||
// setup psuedo-random number generation for all instances of SendQueue
|
||||
static std::random_device rd;
|
||||
|
@ -106,7 +106,7 @@ SendQueue::SendQueue(Socket* socket, HifiSockAddr dest) :
|
|||
}
|
||||
|
||||
SendQueue::~SendQueue() {
|
||||
PROFILE_ASYNC_END(networking, "SendQueue", _destination.toString());
|
||||
PROFILE_ASYNC_END(network, "SendQueue", _destination.toString());
|
||||
}
|
||||
|
||||
void SendQueue::queuePacket(std::unique_ptr<Packet> packet) {
|
||||
|
@ -227,7 +227,7 @@ void SendQueue::sendHandshake() {
|
|||
if (!_hasReceivedHandshakeACK) {
|
||||
// we haven't received a handshake ACK from the client, send another now
|
||||
auto handshakePacket = ControlPacket::create(ControlPacket::Handshake, sizeof(SequenceNumber));
|
||||
PROFILE_ASYNC_BEGIN(networking, "SendQueue:Handshake", _destination.toString());
|
||||
PROFILE_ASYNC_BEGIN(network, "SendQueue:Handshake", _destination.toString());
|
||||
|
||||
handshakePacket->writePrimitive(_initialSequenceNumber);
|
||||
_socket->writeBasePacket(*handshakePacket, _destination);
|
||||
|
@ -244,7 +244,7 @@ void SendQueue::handshakeACK(SequenceNumber initialSequenceNumber) {
|
|||
std::lock_guard<std::mutex> locker { _handshakeMutex };
|
||||
_hasReceivedHandshakeACK = true;
|
||||
}
|
||||
PROFILE_ASYNC_END(networking, "SendQueue:Handshake", _destination.toString());
|
||||
PROFILE_ASYNC_END(network, "SendQueue:Handshake", _destination.toString());
|
||||
|
||||
// Notify on the handshake ACK condition
|
||||
_handshakeACKCondition.notify_one();
|
||||
|
|
|
@ -392,7 +392,6 @@ OctreeElementPointer OctreeElement::addChildAtIndex(int childIndex) {
|
|||
|
||||
_isDirty = true;
|
||||
markWithChangedTime();
|
||||
PROFILE_INSTANT(octree, "EntityAdd", "g");
|
||||
}
|
||||
return childAt;
|
||||
}
|
||||
|
|
|
@ -24,16 +24,16 @@ bool PluginUtils::isHMDAvailable(const QString& pluginName) {
|
|||
return false;
|
||||
}
|
||||
|
||||
bool PluginUtils::isHandControllerAvailable() {
|
||||
bool PluginUtils::isHandControllerAvailable(const QString& pluginName) {
|
||||
for (auto& inputPlugin : PluginManager::getInstance()->getInputPlugins()) {
|
||||
if (inputPlugin->isHandController()) {
|
||||
if (inputPlugin->isHandController() && (pluginName.isEmpty() || inputPlugin->getName() == pluginName)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
};
|
||||
|
||||
bool isSubdeviceContainingNameAvailable(QString name) {
|
||||
bool PluginUtils::isSubdeviceContainingNameAvailable(QString name) {
|
||||
for (auto& inputPlugin : PluginManager::getInstance()->getInputPlugins()) {
|
||||
if (inputPlugin->isActive()) {
|
||||
auto subdeviceNames = inputPlugin->getSubdeviceNames();
|
||||
|
|
|
@ -15,7 +15,8 @@
|
|||
class PluginUtils {
|
||||
public:
|
||||
static bool isHMDAvailable(const QString& pluginName = "");
|
||||
static bool isHandControllerAvailable();
|
||||
static bool isHandControllerAvailable(const QString& pluginName = "");
|
||||
static bool isSubdeviceContainingNameAvailable(QString name);
|
||||
static bool isViveControllerAvailable();
|
||||
static bool isOculusTouchControllerAvailable();
|
||||
static bool isXboxControllerAvailable();
|
||||
|
|
|
@ -793,7 +793,7 @@ void RenderDeferred::configure(const Config& config) {
|
|||
}
|
||||
|
||||
void RenderDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||
PROFILE_RANGE(renderlogging, "DeferredLighting");
|
||||
PROFILE_RANGE(render, "DeferredLighting");
|
||||
|
||||
auto deferredTransform = inputs.get0();
|
||||
auto deferredFramebuffer = inputs.get1();
|
||||
|
|
|
@ -281,7 +281,7 @@ void Model::reset() {
|
|||
}
|
||||
|
||||
bool Model::updateGeometry() {
|
||||
PROFILE_RANGE(renderutils, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("Model::updateGeometry");
|
||||
bool needFullUpdate = false;
|
||||
|
||||
|
@ -476,7 +476,7 @@ bool Model::convexHullContains(glm::vec3 point) {
|
|||
// entity-scripts to call. I think it would be best to do the picking once-per-frame (in cpu, or gpu if possible)
|
||||
// and then the calls use the most recent such result.
|
||||
void Model::recalculateMeshBoxes(bool pickAgainstTriangles) {
|
||||
PROFILE_RANGE(renderutils, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
bool calculatedMeshTrianglesNeeded = pickAgainstTriangles && !_calculatedMeshTrianglesValid;
|
||||
|
||||
if (!_calculatedMeshBoxesValid || calculatedMeshTrianglesNeeded || (!_calculatedMeshPartBoxesValid && pickAgainstTriangles) ) {
|
||||
|
@ -850,6 +850,12 @@ void Model::setTextures(const QVariantMap& textures) {
|
|||
_needsUpdateTextures = true;
|
||||
_needsFixupInScene = true;
|
||||
_renderGeometry->setTextures(textures);
|
||||
} else {
|
||||
// FIXME(Huffman): Disconnect previously connected lambdas so we don't set textures multiple
|
||||
// after the geometry has finished loading.
|
||||
connect(&_renderWatcher, &GeometryResourceWatcher::finished, this, [this, textures]() {
|
||||
_renderGeometry->setTextures(textures);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -969,7 +975,7 @@ Blender::Blender(ModelPointer model, int blendNumber, const Geometry::WeakPointe
|
|||
}
|
||||
|
||||
void Blender::run() {
|
||||
PROFILE_RANGE_EX(renderutils, __FUNCTION__, 0xFFFF0000, 0, { { "url", _model->getURL().toString() } });
|
||||
PROFILE_RANGE_EX(simulation_animation, __FUNCTION__, 0xFFFF0000, 0, { { "url", _model->getURL().toString() } });
|
||||
QVector<glm::vec3> vertices, normals;
|
||||
if (_model) {
|
||||
int offset = 0;
|
||||
|
@ -1090,7 +1096,7 @@ void Model::snapToRegistrationPoint() {
|
|||
}
|
||||
|
||||
void Model::simulate(float deltaTime, bool fullUpdate) {
|
||||
PROFILE_RANGE(renderutils, __FUNCTION__);
|
||||
PROFILE_RANGE(simulation, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("Model::simulate");
|
||||
fullUpdate = updateGeometry() || fullUpdate || (_scaleToFit && !_scaledToFit)
|
||||
|| (_snapModelToRegistrationPoint && !_snappedToRegistrationPoint);
|
||||
|
|
|
@ -21,29 +21,14 @@
|
|||
|
||||
#include <render/CullTask.h>
|
||||
#include <render/SortTask.h>
|
||||
#include <render/DrawTask.h>
|
||||
#include <render/DrawStatus.h>
|
||||
#include <render/DrawSceneOctree.h>
|
||||
#include <render/BlurTask.h>
|
||||
|
||||
#include "LightingModel.h"
|
||||
#include "DebugDeferredBuffer.h"
|
||||
#include "DeferredFramebuffer.h"
|
||||
#include "DeferredLightingEffect.h"
|
||||
#include "SurfaceGeometryPass.h"
|
||||
#include "FramebufferCache.h"
|
||||
#include "HitEffect.h"
|
||||
#include "TextureCache.h"
|
||||
|
||||
#include "AmbientOcclusionEffect.h"
|
||||
#include "AntialiasingEffect.h"
|
||||
#include "ToneMappingEffect.h"
|
||||
#include "SubsurfaceScattering.h"
|
||||
|
||||
#include <gpu/StandardShaderLib.h>
|
||||
|
||||
#include "drawOpaqueStencil_frag.h"
|
||||
|
||||
#include <render/drawItemBounds_vert.h>
|
||||
#include <render/drawItemBounds_frag.h>
|
||||
|
||||
using namespace render;
|
||||
extern void initOverlay3DPipelines(render::ShapePlumber& plumber);
|
||||
|
@ -95,6 +80,8 @@ RenderForwardTask::RenderForwardTask(CullFunctor cullFunctor) {
|
|||
|
||||
const auto framebuffer = addJob<PrepareFramebuffer>("PrepareFramebuffer");
|
||||
|
||||
addJob<DrawBounds>("DrawBounds", opaques);
|
||||
|
||||
// Blit!
|
||||
addJob<Blit>("Blit", framebuffer);
|
||||
}
|
||||
|
@ -151,13 +138,62 @@ void PrepareFramebuffer::run(const SceneContextPointer& sceneContext, const Rend
|
|||
batch.setFramebuffer(_framebuffer);
|
||||
batch.clearFramebuffer(
|
||||
gpu::Framebuffer::BUFFER_COLOR0 |
|
||||
gpu::Framebuffer::BUFFER_COLOR1 |
|
||||
gpu::Framebuffer::BUFFER_COLOR2 |
|
||||
gpu::Framebuffer::BUFFER_COLOR3 |
|
||||
gpu::Framebuffer::BUFFER_DEPTH |
|
||||
gpu::Framebuffer::BUFFER_STENCIL,
|
||||
vec4(vec3(0), 0), 1.0, 0.0, true);
|
||||
vec4(vec3(0), 1), 1.0, 0.0, true);
|
||||
});
|
||||
|
||||
framebuffer = _framebuffer;
|
||||
}
|
||||
|
||||
const gpu::PipelinePointer DrawBounds::getPipeline() {
|
||||
if (!_boundsPipeline) {
|
||||
auto vs = gpu::Shader::createVertex(std::string(drawItemBounds_vert));
|
||||
auto ps = gpu::Shader::createPixel(std::string(drawItemBounds_frag));
|
||||
gpu::ShaderPointer program = gpu::Shader::createProgram(vs, ps);
|
||||
|
||||
gpu::Shader::BindingSet slotBindings;
|
||||
gpu::Shader::makeProgram(*program, slotBindings);
|
||||
|
||||
_cornerLocation = program->getUniforms().findLocation("inBoundPos");
|
||||
_scaleLocation = program->getUniforms().findLocation("inBoundDim");
|
||||
|
||||
auto state = std::make_shared<gpu::State>();
|
||||
state->setDepthTest(true, false, gpu::LESS_EQUAL);
|
||||
state->setBlendFunction(true,
|
||||
gpu::State::SRC_ALPHA, gpu::State::BLEND_OP_ADD, gpu::State::INV_SRC_ALPHA,
|
||||
gpu::State::DEST_ALPHA, gpu::State::BLEND_OP_ADD, gpu::State::ZERO);
|
||||
|
||||
_boundsPipeline = gpu::Pipeline::create(program, state);
|
||||
}
|
||||
return _boundsPipeline;
|
||||
}
|
||||
|
||||
void DrawBounds::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& items) {
|
||||
RenderArgs* args = renderContext->args;
|
||||
|
||||
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
||||
// Setup projection
|
||||
glm::mat4 projMat;
|
||||
Transform viewMat;
|
||||
args->getViewFrustum().evalProjectionMatrix(projMat);
|
||||
args->getViewFrustum().evalViewTransform(viewMat);
|
||||
batch.setProjectionTransform(projMat);
|
||||
batch.setViewTransform(viewMat);
|
||||
batch.setModelTransform(Transform());
|
||||
|
||||
// Bind program
|
||||
batch.setPipeline(getPipeline());
|
||||
assert(_cornerLocation >= 0);
|
||||
assert(_scaleLocation >= 0);
|
||||
|
||||
// Render bounds
|
||||
for (const auto& item : items) {
|
||||
batch._glUniform3fv(_cornerLocation, 1, (const float*)(&item.bound.getCorner()));
|
||||
batch._glUniform3fv(_scaleLocation, 1, (const float*)(&item.bound.getScale()));
|
||||
|
||||
static const int NUM_VERTICES_PER_CUBE = 24;
|
||||
batch.draw(gpu::LINES, NUM_VERTICES_PER_CUBE, 0);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
|
@ -39,4 +39,18 @@ private:
|
|||
gpu::FramebufferPointer _framebuffer;
|
||||
};
|
||||
|
||||
#endif // hifi_RenderForwardTask_h
|
||||
class DrawBounds {
|
||||
public:
|
||||
using Inputs = render::ItemBounds;
|
||||
using JobModel = render::Job::ModelI<DrawBounds, Inputs>;
|
||||
|
||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& items);
|
||||
|
||||
private:
|
||||
const gpu::PipelinePointer getPipeline();
|
||||
gpu::PipelinePointer _boundsPipeline;
|
||||
int _cornerLocation { -1 };
|
||||
int _scaleLocation { -1 };
|
||||
};
|
||||
|
||||
#endif // hifi_RenderForwardTask_h
|
|
@ -78,13 +78,16 @@ void consolidateChangeQueue(PendingChangesQueue& queue, PendingChanges& singleBa
|
|||
}
|
||||
|
||||
void Scene::processPendingChangesQueue() {
|
||||
PROFILE_RANGE(renderlogging, __FUNCTION__);
|
||||
_changeQueueMutex.lock();
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
PendingChanges consolidatedPendingChanges;
|
||||
consolidateChangeQueue(_changeQueue, consolidatedPendingChanges);
|
||||
_changeQueueMutex.unlock();
|
||||
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(_changeQueueMutex);
|
||||
consolidateChangeQueue(_changeQueue, consolidatedPendingChanges);
|
||||
}
|
||||
|
||||
_itemsMutex.lock();
|
||||
{
|
||||
std::unique_lock<std::mutex> lock(_itemsMutex);
|
||||
// Here we should be able to check the value of last ItemID allocated
|
||||
// and allocate new items accordingly
|
||||
ItemID maxID = _IDAllocator.load();
|
||||
|
@ -108,9 +111,7 @@ void Scene::processPendingChangesQueue() {
|
|||
|
||||
// Update the numItemsAtomic counter AFTER the pending changes went through
|
||||
_numAllocatedItems.exchange(maxID);
|
||||
|
||||
// ready to go back to rendering activities
|
||||
_itemsMutex.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
void Scene::resetItems(const ItemIDs& ids, Payloads& payloads) {
|
||||
|
|
|
@ -572,7 +572,7 @@ public:
|
|||
|
||||
void run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext) {
|
||||
PerformanceTimer perfTimer(_name.c_str());
|
||||
PROFILE_RANGE(renderlogging, _name.c_str());
|
||||
PROFILE_RANGE(render, _name.c_str());
|
||||
auto start = usecTimestampNow();
|
||||
|
||||
_concept->run(sceneContext, renderContext);
|
||||
|
|
|
@ -8,6 +8,17 @@
|
|||
|
||||
#include "Profile.h"
|
||||
|
||||
Q_LOGGING_CATEGORY(trace_app, "trace.app")
|
||||
Q_LOGGING_CATEGORY(trace_network, "trace.network")
|
||||
Q_LOGGING_CATEGORY(trace_parse, "trace.parse")
|
||||
Q_LOGGING_CATEGORY(trace_render, "trace.render")
|
||||
Q_LOGGING_CATEGORY(trace_render_gpu, "trace.render.gpu")
|
||||
Q_LOGGING_CATEGORY(trace_resource, "trace.resource")
|
||||
Q_LOGGING_CATEGORY(trace_resource_network, "trace.resource.network")
|
||||
Q_LOGGING_CATEGORY(trace_resource_parse, "trace.resource.parse")
|
||||
Q_LOGGING_CATEGORY(trace_simulation, "trace.simulation")
|
||||
Q_LOGGING_CATEGORY(trace_simulation_animation, "trace.simulation.animation")
|
||||
Q_LOGGING_CATEGORY(trace_simulation_physics, "trace.simulation.physics")
|
||||
|
||||
#if defined(NSIGHT_FOUND)
|
||||
#include "nvToolsExt.h"
|
||||
|
|
|
@ -11,6 +11,18 @@
|
|||
#define HIFI_PROFILE_
|
||||
|
||||
#include "Trace.h"
|
||||
#include "SharedUtil.h"
|
||||
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_app)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_network)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_render)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_render_gpu)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_resource)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_resource_parse)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_resource_network)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_simulation)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_simulation_animation)
|
||||
Q_DECLARE_LOGGING_CATEGORY(trace_simulation_physics)
|
||||
|
||||
class Duration {
|
||||
public:
|
||||
|
@ -51,13 +63,18 @@ inline void counter(const QLoggingCategory& category, const QString& name, const
|
|||
}
|
||||
}
|
||||
|
||||
#define PROFILE_RANGE(category, name) Duration profileRangeThis(category(), name);
|
||||
#define PROFILE_RANGE_EX(category, name, argbColor, payload, ...) Duration profileRangeThis(category(), name, argbColor, (uint64_t)payload, ##__VA_ARGS__);
|
||||
#define PROFILE_RANGE_BEGIN(category, rangeId, name, argbColor) rangeId = Duration::beginRange(category(), name, argbColor)
|
||||
#define PROFILE_RANGE_END(category, rangeId) Duration::endRange(category(), rangeId)
|
||||
#define PROFILE_ASYNC_BEGIN(category, name, id, ...) asyncBegin(category(), name, id, ##__VA_ARGS__);
|
||||
#define PROFILE_ASYNC_END(category, name, id, ...) asyncEnd(category(), name, id, ##__VA_ARGS__);
|
||||
#define PROFILE_COUNTER(category, name, ...) counter(category(), name, ##__VA_ARGS__);
|
||||
#define PROFILE_INSTANT(category, name, ...) instant(category(), name, ##__VA_ARGS__);
|
||||
#define PROFILE_RANGE(category, name) Duration profileRangeThis(trace_##category(), name);
|
||||
#define PROFILE_RANGE_EX(category, name, argbColor, payload, ...) Duration profileRangeThis(trace_##category(), name, argbColor, (uint64_t)payload, ##__VA_ARGS__);
|
||||
#define PROFILE_RANGE_BEGIN(category, rangeId, name, argbColor) rangeId = Duration::beginRange(trace_##category(), name, argbColor)
|
||||
#define PROFILE_RANGE_END(category, rangeId) Duration::endRange(trace_##category(), rangeId)
|
||||
#define PROFILE_ASYNC_BEGIN(category, name, id, ...) asyncBegin(trace_##category(), name, id, ##__VA_ARGS__);
|
||||
#define PROFILE_ASYNC_END(category, name, id, ...) asyncEnd(trace_##category(), name, id, ##__VA_ARGS__);
|
||||
#define PROFILE_COUNTER(category, name, ...) counter(trace_##category(), name, ##__VA_ARGS__);
|
||||
#define PROFILE_INSTANT(category, name, ...) instant(trace_##category(), name, ##__VA_ARGS__);
|
||||
|
||||
#define SAMPLE_PROFILE_RANGE(chance, category, name, ...) if (randFloat() <= chance) { PROFILE_RANGE(category, name); }
|
||||
#define SAMPLE_PROFILE_RANGE_EX(chance, category, name, ...) if (randFloat() <= chance) { PROFILE_RANGE_EX(category, name, argbColor, payload, ##__VA_ARGS__); }
|
||||
#define SAMPLE_PROFILE_COUNTER(chance, category, name, ...) if (randFloat() <= chance) { PROFILE_COUNTER(category, name, ##__VA_ARGS__); }
|
||||
#define SAMPLE_PROFILE_INSTANT(chance, category, name, ...) if (randFloat() <= chance) { PROFILE_INSTANT(category, name, ##__VA_ARGS__); }
|
||||
|
||||
#endif
|
||||
|
|
|
@ -13,6 +13,9 @@
|
|||
#include <QtCore/QDebug>
|
||||
#include <QtCore/QCoreApplication>
|
||||
#include <QtCore/QThread>
|
||||
#include <QtCore/QFileInfo>
|
||||
#include <QtCore/QDir>
|
||||
#include <QtCore/QStandardPaths>
|
||||
|
||||
#include <QtCore/QFile>
|
||||
#include <QtCore/QFileInfo>
|
||||
|
@ -100,7 +103,24 @@ void TraceEvent::writeJson(QTextStream& out) const {
|
|||
#endif
|
||||
}
|
||||
|
||||
void Tracer::serialize(const QString& path) {
|
||||
void Tracer::serialize(const QString& originalPath) {
|
||||
|
||||
QString path = originalPath;
|
||||
|
||||
// If the filename is relative, turn it into an absolute path relative to the document directory.
|
||||
QFileInfo originalFileInfo(path);
|
||||
if (originalFileInfo.isRelative()) {
|
||||
QString docsLocation = QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation);
|
||||
path = docsLocation + "/" + path;
|
||||
QFileInfo info(path);
|
||||
if (!info.absoluteDir().exists()) {
|
||||
QString originalRelativePath = originalFileInfo.path();
|
||||
QDir(docsLocation).mkpath(originalRelativePath);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
std::list<TraceEvent> currentEvents;
|
||||
{
|
||||
std::lock_guard<std::mutex> guard(_eventsMutex);
|
||||
|
|
|
@ -21,8 +21,6 @@
|
|||
|
||||
#include "DependencyManager.h"
|
||||
|
||||
#define TRACE_ENABLED
|
||||
|
||||
namespace tracing {
|
||||
|
||||
bool enabled();
|
||||
|
|
|
@ -110,7 +110,7 @@ void OculusDisplayPlugin::hmdPresent() {
|
|||
return;
|
||||
}
|
||||
|
||||
PROFILE_RANGE_EX(displayplugins, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
|
||||
int curIndex;
|
||||
ovr_GetTextureSwapChainCurrentIndex(_session, _textureSwapChain, &curIndex);
|
||||
|
|
|
@ -529,7 +529,7 @@ static bool isBadPose(vr::HmdMatrix34_t* mat) {
|
|||
}
|
||||
|
||||
bool OpenVrDisplayPlugin::beginFrameRender(uint32_t frameIndex) {
|
||||
PROFILE_RANGE_EX(displayplugins, __FUNCTION__, 0xff7fff00, frameIndex)
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff7fff00, frameIndex)
|
||||
handleOpenVrEvents();
|
||||
if (openVrQuitRequested()) {
|
||||
QMetaObject::invokeMethod(qApp, "quit");
|
||||
|
@ -633,7 +633,7 @@ void OpenVrDisplayPlugin::compositeLayers() {
|
|||
}
|
||||
|
||||
void OpenVrDisplayPlugin::hmdPresent() {
|
||||
PROFILE_RANGE_EX(displayplugins, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
|
||||
if (_threadedSubmit) {
|
||||
_submitThread->waitForPresent();
|
||||
|
@ -654,7 +654,7 @@ void OpenVrDisplayPlugin::hmdPresent() {
|
|||
}
|
||||
|
||||
void OpenVrDisplayPlugin::postPreview() {
|
||||
PROFILE_RANGE_EX(displayplugins, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
PROFILE_RANGE_EX(render, __FUNCTION__, 0xff00ff00, (uint64_t)_currentFrame->frameIndex)
|
||||
PoseData nextRender, nextSim;
|
||||
nextRender.frameIndex = presentCount();
|
||||
|
||||
|
|
|
@ -21,14 +21,17 @@ function clamp(value, min, max) {
|
|||
}
|
||||
|
||||
function resolveHardware(path) {
|
||||
var parts = path.split(".");
|
||||
function resolveInner(base, path, i) {
|
||||
if (i >= path.length) {
|
||||
return base;
|
||||
if (typeof path === 'string') {
|
||||
var parts = path.split(".");
|
||||
function resolveInner(base, path, i) {
|
||||
if (i >= path.length) {
|
||||
return base;
|
||||
}
|
||||
return resolveInner(base[path[i]], path, ++i);
|
||||
}
|
||||
return resolveInner(base[path[i]], path, ++i);
|
||||
return resolveInner(Controller.Hardware, parts, 0);
|
||||
}
|
||||
return resolveInner(Controller.Hardware, parts, 0);
|
||||
return path;
|
||||
}
|
||||
|
||||
var DEBUG = true;
|
||||
|
@ -132,7 +135,9 @@ createControllerDisplay = function(config) {
|
|||
overlayID = Overlays.addOverlay("model", properties);
|
||||
|
||||
if (part.type === "rotational") {
|
||||
mapping.from([part.input]).peek().to(function(controller, overlayID, part) {
|
||||
var input = resolveHardware(part.input);
|
||||
print("Mapping to: ", part.input, input);
|
||||
mapping.from([input]).peek().to(function(controller, overlayID, part) {
|
||||
return function(value) {
|
||||
value = clamp(value, part.minValue, part.maxValue);
|
||||
|
||||
|
@ -157,18 +162,85 @@ createControllerDisplay = function(config) {
|
|||
}(controller, overlayID, part));
|
||||
} else if (part.type === "touchpad") {
|
||||
var visibleInput = resolveHardware(part.visibleInput);
|
||||
var xinput = resolveHardware(part.xInput);
|
||||
var yinput = resolveHardware(part.yInput);
|
||||
var xInput = resolveHardware(part.xInput);
|
||||
var yInput = resolveHardware(part.yInput);
|
||||
|
||||
// TODO: Touchpad inputs are currently only working for half
|
||||
// of the touchpad. When that is fixed, it would be useful
|
||||
// to update these to display the current finger position.
|
||||
mapping.from([visibleInput]).peek().to(function(value) {
|
||||
});
|
||||
mapping.from([xinput]).peek().to(function(value) {
|
||||
mapping.from([xInput]).peek().to(function(value) {
|
||||
});
|
||||
mapping.from([yinput]).peek().invert().to(function(value) {
|
||||
mapping.from([yInput]).peek().invert().to(function(value) {
|
||||
});
|
||||
} else if (part.type === "joystick") {
|
||||
(function(controller, overlayID, part) {
|
||||
const xInput = resolveHardware(part.xInput);
|
||||
const yInput = resolveHardware(part.yInput);
|
||||
|
||||
var xvalue = 0;
|
||||
var yvalue = 0;
|
||||
|
||||
function calculatePositionAndRotation(xValue, yValue) {
|
||||
var rotation = Quat.fromPitchYawRollDegrees(yValue * part.xHalfAngle, 0, xValue * part.yHalfAngle);
|
||||
|
||||
var offset = { x: 0, y: 0, z: 0 };
|
||||
if (part.originOffset) {
|
||||
offset = Vec3.multiplyQbyV(rotation, part.originOffset);
|
||||
offset = Vec3.subtract(part.originOffset, offset);
|
||||
}
|
||||
|
||||
var partPosition = Vec3.sum(controller.position,
|
||||
Vec3.multiplyQbyV(controller.rotation, Vec3.sum(offset, part.naturalPosition)));
|
||||
|
||||
var partRotation = Quat.multiply(controller.rotation, rotation)
|
||||
|
||||
return {
|
||||
position: partPosition,
|
||||
rotation: partRotation
|
||||
}
|
||||
}
|
||||
|
||||
mapping.from([xInput]).peek().to(function(value) {
|
||||
xvalue = value;
|
||||
//print(overlayID, xvalue.toFixed(3), yvalue.toFixed(3));
|
||||
var posRot = calculatePositionAndRotation(xvalue, yvalue);
|
||||
Overlays.editOverlay(overlayID, {
|
||||
localPosition: posRot.position,
|
||||
localRotation: posRot.rotation
|
||||
});
|
||||
});
|
||||
|
||||
mapping.from([yInput]).peek().to(function(value) {
|
||||
yvalue = value;
|
||||
var posRot = calculatePositionAndRotation(xvalue, yvalue);
|
||||
Overlays.editOverlay(overlayID, {
|
||||
localPosition: posRot.position,
|
||||
localRotation: posRot.rotation
|
||||
});
|
||||
});
|
||||
})(controller, overlayID, part);
|
||||
|
||||
} else if (part.type === "linear") {
|
||||
(function(controller, overlayID, part) {
|
||||
const input = resolveHardware(part.input);
|
||||
|
||||
mapping.from([input]).peek().to(function(value) {
|
||||
//print(value);
|
||||
var axis = Vec3.multiplyQbyV(controller.rotation, part.axis);
|
||||
var offset = Vec3.multiply(part.maxTranslation * value, axis);
|
||||
|
||||
var partPosition = Vec3.sum(controller.position, Vec3.multiplyQbyV(controller.rotation, part.naturalPosition));
|
||||
var position = Vec3.sum(partPosition, offset);
|
||||
|
||||
Overlays.editOverlay(overlayID, {
|
||||
localPosition: position
|
||||
});
|
||||
});
|
||||
|
||||
})(controller, overlayID, part);
|
||||
|
||||
} else if (part.type === "static") {
|
||||
// do nothing
|
||||
} else {
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
|
||||
Script.include("controllerDisplay.js");
|
||||
Script.include("viveControllerConfiguration.js");
|
||||
Script.include("touchControllerConfiguration.js");
|
||||
|
||||
var HIDE_CONTROLLERS_ON_EQUIP = false;
|
||||
|
||||
|
@ -41,12 +42,28 @@ ControllerDisplayManager = function() {
|
|||
|
||||
function updateControllers() {
|
||||
if (HMD.active && HMD.shouldShowHandControllers()) {
|
||||
var leftConfig = null;
|
||||
var rightConfig = null;
|
||||
|
||||
if ("Vive" in Controller.Hardware) {
|
||||
if (!controllerLeft) {
|
||||
controllerLeft = createControllerDisplay(VIVE_CONTROLLER_CONFIGURATION_LEFT);
|
||||
leftConfig = VIVE_CONTROLLER_CONFIGURATION_LEFT;
|
||||
rightConfig = VIVE_CONTROLLER_CONFIGURATION_RIGHT;
|
||||
}
|
||||
|
||||
if ("OculusTouch" in Controller.Hardware) {
|
||||
leftConfig = TOUCH_CONTROLLER_CONFIGURATION_LEFT;
|
||||
rightConfig = TOUCH_CONTROLLER_CONFIGURATION_RIGHT;
|
||||
}
|
||||
|
||||
if (leftConfig !== null && rightConfig !== null) {
|
||||
print("Loading controllers");
|
||||
if (controllerLeft === null) {
|
||||
controllerLeft = createControllerDisplay(leftConfig);
|
||||
controllerLeft.setVisible(true);
|
||||
}
|
||||
if (!controllerRight) {
|
||||
controllerRight = createControllerDisplay(VIVE_CONTROLLER_CONFIGURATION_RIGHT);
|
||||
if (controllerRight === null) {
|
||||
controllerRight = createControllerDisplay(rightConfig);
|
||||
controllerRight.setVisible(true);
|
||||
}
|
||||
// We've found the controllers, we no longer need to look for active controllers
|
||||
if (controllerCheckerIntervalID) {
|
||||
|
|
353
scripts/system/controllers/touchControllerConfiguration.js
Normal file
353
scripts/system/controllers/touchControllerConfiguration.js
Normal file
|
@ -0,0 +1,353 @@
|
|||
|
||||
//
|
||||
// touchControllerConfiguration.js
|
||||
//
|
||||
// Created by Ryan Huffman on 12/06/16
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
|
||||
/* globals TOUCH_CONTROLLER_CONFIGURATION_LEFT:true TOUCH_CONTROLLER_CONFIGURATION_RIGHT:true */
|
||||
/* eslint camelcase: ["error", { "properties": "never" }] */
|
||||
|
||||
var leftBaseRotation = Quat.multiply(
|
||||
Quat.fromPitchYawRollDegrees(-90, 0, 0),
|
||||
Quat.fromPitchYawRollDegrees(0, 0, 90)
|
||||
);
|
||||
var rightBaseRotation = Quat.multiply(
|
||||
Quat.fromPitchYawRollDegrees(-90, 0, 0),
|
||||
Quat.fromPitchYawRollDegrees(0, 0, -90)
|
||||
);
|
||||
|
||||
// keep these in sync with the values from OculusHelpers.cpp
|
||||
var CONTROLLER_LENGTH_OFFSET = 0.0762;
|
||||
var CONTROLLER_LATERAL_OFFSET = 0.0381;
|
||||
var CONTROLLER_VERTICAL_OFFSET = 0.0381;
|
||||
var CONTROLLER_FORWARD_OFFSET = 0.1524;
|
||||
|
||||
var leftBasePosition = Vec3.multiplyQbyV(leftBaseRotation, {
|
||||
x: -CONTROLLER_LENGTH_OFFSET / 2.0,
|
||||
y: CONTROLLER_LENGTH_OFFSET / 2.0,
|
||||
z: CONTROLLER_LENGTH_OFFSET * 1.5
|
||||
});
|
||||
var rightBasePosition = Vec3.multiplyQbyV(rightBaseRotation, {
|
||||
x: CONTROLLER_LENGTH_OFFSET / 2.0,
|
||||
y: CONTROLLER_LENGTH_OFFSET / 2.0,
|
||||
z: CONTROLLER_LENGTH_OFFSET * 1.5
|
||||
});
|
||||
|
||||
var BASE_URL = Script.resourcesPath() + "meshes/controller/touch/";
|
||||
|
||||
TOUCH_CONTROLLER_CONFIGURATION_LEFT = {
|
||||
name: "Touch",
|
||||
controllers: [
|
||||
{
|
||||
modelURL: BASE_URL + "touch_l_body.fbx",
|
||||
jointIndex: MyAvatar.getJointIndex("_CONTROLLER_LEFTHAND"),
|
||||
naturalPosition: { x: 0.01648625358939171, y: -0.03551870584487915, z: -0.018527675420045853 },
|
||||
dimensions: { x: 0.11053799837827682, y: 0.0995776429772377, z: 0.10139888525009155 },
|
||||
rotation: leftBaseRotation,
|
||||
position: leftBasePosition,
|
||||
|
||||
parts: {
|
||||
tips: {
|
||||
type: "static",
|
||||
modelURL: BASE_URL + "Oculus-Labels-L.fbx",
|
||||
naturalPosition: { x: -0.022335469722747803, y: 0.00022516027092933655, z: 0.020340695977211 },
|
||||
|
||||
textureName: "blank",
|
||||
defaultTextureLayer: "blank",
|
||||
textureLayers: {
|
||||
blank: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-L.fbx/Oculus-Labels-L.fbm/Blank.png"
|
||||
},
|
||||
trigger: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-L.fbx/Oculus-Labels-L.fbm/Trigger.png"
|
||||
},
|
||||
arrows: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-L.fbx/Oculus-Labels-L.fbm/Rotate.png"
|
||||
},
|
||||
grip: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-L.fbx/Oculus-Labels-L.fbm/Grip-oculus.png"
|
||||
},
|
||||
teleport: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-L.fbx/Oculus-Labels-L.fbm/Teleport.png"
|
||||
},
|
||||
}
|
||||
},
|
||||
|
||||
trigger: {
|
||||
type: "rotational",
|
||||
modelURL: BASE_URL + "touch_l_trigger.fbx",
|
||||
naturalPosition: { x: 0.0008544912561774254, y: -0.019867943599820137, z: 0.018800459802150726 },
|
||||
|
||||
// rotational
|
||||
input: Controller.Standard.LT,
|
||||
origin: { x: 0, y: -0.015, z: -0.00 },
|
||||
minValue: 0.0,
|
||||
maxValue: 1.0,
|
||||
axis: { x: 1, y: 0, z: 0 },
|
||||
maxAngle: 17,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_trigger.fbx/touch_l_trigger.fbm/L_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_trigger.fbx/touch_l_trigger.fbm/L_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
grip: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_l_bumper.fbx",
|
||||
naturalPosition: { x: 0.00008066371083259583, y: -0.02715788595378399, z: -0.02448512241244316 },
|
||||
|
||||
// linear properties
|
||||
// Offset from origin = 0.36470, 0.11048, 0.11066
|
||||
input: "OculusTouch.LeftGrip",
|
||||
axis: { x: 1, y: 0.302933918, z: 0.302933918 },
|
||||
maxTranslation: 0.003967,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_bumper.fbx/touch_l_bumper.fbm/L_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_bumper.fbx/touch_l_bumper.fbm/L_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
joystick: {
|
||||
type: "joystick",
|
||||
modelURL: BASE_URL + "touch_l_joystick.fbx",
|
||||
naturalPosition: { x: 0.0075613949447870255, y: -0.008225866593420506, z: 0.004792703315615654 },
|
||||
|
||||
// joystick
|
||||
xInput: "OculusTouch.LX",
|
||||
yInput: "OculusTouch.LY",
|
||||
originOffset: { x: 0, y: -0.0028564, z: -0.00 },
|
||||
xHalfAngle: 20,
|
||||
yHalfAngle: 20,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_joystick.fbx/touch_l_joystick.fbm/L_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_joystick.fbx/touch_l_joystick.fbm/L_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
button_a: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_l_button_x.fbx",
|
||||
naturalPosition: { x: -0.009307309985160828, y: -0.00005015172064304352, z: -0.012594521045684814 },
|
||||
|
||||
input: "OculusTouch.X",
|
||||
axis: { x: 0, y: -1, z: 0 },
|
||||
maxTranslation: 0.001,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_button_x.fbx/touch_l_button_x.fbm/L_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_button_x.fbx/touch_l_button_x.fbm/L_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
button_b: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_l_button_y.fbx",
|
||||
naturalPosition: { x: -0.01616849936544895, y: -0.000050364527851343155, z: 0.0017703399062156677 },
|
||||
|
||||
input: "OculusTouch.Y",
|
||||
axis: { x: 0, y: -1, z: 0 },
|
||||
maxTranslation: 0.001,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_button_y.fbx/touch_l_button_y.fbm/L_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_l_button_y.fbx/touch_l_button_y.fbm/L_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
]
|
||||
};
|
||||
|
||||
TOUCH_CONTROLLER_CONFIGURATION_RIGHT = {
|
||||
name: "Touch",
|
||||
controllers: [
|
||||
{
|
||||
modelURL: BASE_URL + "touch_r_body.fbx",
|
||||
jointIndex: MyAvatar.getJointIndex("_CONTROLLER_RIGHTHAND"),
|
||||
naturalPosition: { x: -0.016486231237649918, y: -0.03551865369081497, z: -0.018527653068304062 },
|
||||
dimensions: { x: 0.11053784191608429, y: 0.09957750141620636, z: 0.10139875113964081 },
|
||||
rotation: rightBaseRotation,
|
||||
position: rightBasePosition,
|
||||
|
||||
parts: {
|
||||
tips: {
|
||||
type: "static",
|
||||
modelURL: BASE_URL + "Oculus-Labels-R.fbx",
|
||||
naturalPosition: { x: 0.009739525616168976, y: -0.0017818436026573181, z: 0.016794726252555847 },
|
||||
|
||||
textureName: "Texture",
|
||||
defaultTextureLayer: "blank",
|
||||
textureLayers: {
|
||||
blank: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-R.fbx/Oculus-Labels-R.fbm/Blank.png"
|
||||
},
|
||||
trigger: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-R.fbx/Oculus-Labels-R.fbm/Trigger.png"
|
||||
},
|
||||
arrows: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-R.fbx/Oculus-Labels-R.fbm/Rotate.png"
|
||||
},
|
||||
grip: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-R.fbx/Oculus-Labels-R.fbm/Grip-oculus.png"
|
||||
},
|
||||
teleport: {
|
||||
defaultTextureURL: BASE_URL + "Oculus-Labels-R.fbx/Oculus-Labels-R.fbm/Teleport.png"
|
||||
},
|
||||
}
|
||||
},
|
||||
|
||||
trigger: {
|
||||
type: "rotational",
|
||||
modelURL: BASE_URL + "touch_r_trigger.fbx",
|
||||
naturalPosition: { x: -0.0008544912561774254, y: -0.019867943599820137, z: 0.018800459802150726 },
|
||||
|
||||
// rotational
|
||||
input: "OculusTouch.RT",
|
||||
origin: { x: 0, y: -0.015, z: 0 },
|
||||
minValue: 0.0,
|
||||
maxValue: 1.0,
|
||||
axis: { x: 1, y: 0, z: 0 },
|
||||
maxAngle: 17,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_trigger.fbx/touch_r_trigger.fbm/R_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_trigger.fbx/touch_r_trigger.fbm/R_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
grip: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_r_bumper.fbx",
|
||||
naturalPosition: { x: -0.0000806618481874466, y: -0.027157839387655258, z: -0.024485092610120773 },
|
||||
|
||||
// linear properties
|
||||
// Offset from origin = 0.36470, 0.11048, 0.11066
|
||||
input: "OculusTouch.RightGrip",
|
||||
axis: { x: -1, y: 0.302933918, z: 0.302933918 },
|
||||
maxTranslation: 0.003967,
|
||||
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_bumper.fbx/touch_r_bumper.fbm/R_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_bumper.fbx/touch_r_bumper.fbm/R_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
joystick: {
|
||||
type: "joystick",
|
||||
modelURL: BASE_URL + "touch_r_joystick.fbx",
|
||||
naturalPosition: { x: -0.007561382371932268, y: -0.008225853554904461, z: 0.00479268841445446 },
|
||||
|
||||
// joystick
|
||||
xInput: "OculusTouch.RX",
|
||||
yInput: "OculusTouch.RY",
|
||||
originOffset: { x: 0, y: -0.0028564, z: 0 },
|
||||
xHalfAngle: 20,
|
||||
yHalfAngle: 20,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_joystick.fbx/touch_r_joystick.fbm/R_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_joystick.fbx/touch_r_joystick.fbm/R_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
button_a: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_r_button_a.fbx",
|
||||
naturalPosition: { x: 0.009307296946644783, y: -0.00005015172064304352, z: -0.012594504281878471 },
|
||||
|
||||
input: "OculusTouch.A",
|
||||
axis: { x: 0, y: -1, z: 0 },
|
||||
maxTranslation: 0.001,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_button_a.fbx/touch_r_button_a.fbm/R_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_button_a.fbx/touch_r_button_a.fbm/R_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
button_b: {
|
||||
type: "linear",
|
||||
modelURL: BASE_URL + "touch_r_button_b.fbx",
|
||||
naturalPosition: { x: 0.01616847701370716, y: -0.000050364527851343155, z: 0.0017703361809253693 },
|
||||
|
||||
input: "OculusTouch.B",
|
||||
axis: { x: 0, y: -1, z: 0 },
|
||||
maxTranslation: 0.001,
|
||||
|
||||
textureName: "tex-highlight",
|
||||
defaultTextureLayer: "normal",
|
||||
textureLayers: {
|
||||
normal: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_button_b.fbx/touch_r_button_b.fbm/R_controller_DIF.jpg",
|
||||
},
|
||||
highlight: {
|
||||
defaultTextureURL: BASE_URL + "touch_r_button_b.fbx/touch_r_button_b.fbm/R_controller-highlight_DIF.jpg",
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
]
|
||||
};
|
|
@ -83,7 +83,6 @@ VIVE_CONTROLLER_CONFIGURATION_LEFT = {
|
|||
naturalPosition: {"x":-0.004377640783786774,"y":-0.034371938556432724,"z":0.06769277155399323},
|
||||
|
||||
textureName: "Tex.Blank",
|
||||
|
||||
defaultTextureLayer: "blank",
|
||||
textureLayers: {
|
||||
blank: {
|
||||
|
|
|
@ -900,7 +900,7 @@ private:
|
|||
gpu::doInBatch(gpuContext, [&](gpu::Batch& batch) {
|
||||
batch.resetStages();
|
||||
});
|
||||
PROFILE_RANGE(renderperflogging, __FUNCTION__);
|
||||
PROFILE_RANGE(render, __FUNCTION__);
|
||||
PerformanceTimer perfTimer("draw");
|
||||
// The pending changes collecting the changes here
|
||||
render::PendingChanges pendingChanges;
|
||||
|
|
|
@ -9,33 +9,35 @@
|
|||
#include "TraceTests.h"
|
||||
|
||||
#include <QtTest/QtTest>
|
||||
#include <Trace.h>
|
||||
#include <QtGui/QDesktopServices>
|
||||
|
||||
#include <Profile.h>
|
||||
|
||||
#include <SharedUtil.h>
|
||||
#include <NumericalConstants.h>
|
||||
#include <../QTestExtensions.h>
|
||||
|
||||
QTEST_MAIN(TraceTests)
|
||||
Q_LOGGING_CATEGORY(tracertestlogging, "hifi.tracer.test")
|
||||
Q_LOGGING_CATEGORY(trace_test, "trace.test")
|
||||
|
||||
const QString OUTPUT_FILE = "traces/testTrace.json.gz";
|
||||
|
||||
void TraceTests::testTraceSerialization() {
|
||||
auto tracer = DependencyManager::set<tracing::Tracer>();
|
||||
tracer->startTracing();
|
||||
tracer->traceEvent(tracertestlogging(), "TestEvent", tracing::DurationBegin);
|
||||
{
|
||||
auto start = usecTimestampNow();
|
||||
PROFILE_RANGE(test, "TestEvent")
|
||||
for (size_t i = 0; i < 10000; ++i) {
|
||||
tracer->traceEvent(tracertestlogging(), "TestCounter", tracing::Counter, "", { { "i", i } });
|
||||
SAMPLE_PROFILE_COUNTER(0.1f, test, "TestCounter", { { "i", i } })
|
||||
}
|
||||
auto duration = usecTimestampNow() - start;
|
||||
duration /= USECS_PER_MSEC;
|
||||
qDebug() << "Recording took " << duration << "ms";
|
||||
}
|
||||
tracer->traceEvent(tracertestlogging(), "TestEvent", tracing::DurationEnd);
|
||||
tracer->stopTracing();
|
||||
{
|
||||
auto start = usecTimestampNow();
|
||||
tracer->serialize("testTrace.json.gz");
|
||||
tracer->serialize(OUTPUT_FILE);
|
||||
auto duration = usecTimestampNow() - start;
|
||||
duration /= USECS_PER_MSEC;
|
||||
qDebug() << "Serialization took " << duration << "ms";
|
||||
|
|
|
@ -58,11 +58,6 @@ function info() {
|
|||
}
|
||||
}
|
||||
|
||||
// Return a number between min (inclusive) and max (exclusive)
|
||||
function randomInt(min, max) {
|
||||
return min + Math.floor(Math.random() * (max - min))
|
||||
}
|
||||
|
||||
var NEAR_BOX_SPAWN_NAME = "tutorial/nearGrab/box_spawn";
|
||||
var FAR_BOX_SPAWN_NAME = "tutorial/farGrab/box_spawn";
|
||||
var GUN_SPAWN_NAME = "tutorial/gun_spawn";
|
||||
|
@ -78,10 +73,6 @@ function setAwayEnabled(value) {
|
|||
Messages.sendLocalMessage(CHANNEL_AWAY_ENABLE, message);
|
||||
}
|
||||
|
||||
function beginsWithFilter(value, key) {
|
||||
return value.indexOf(properties[key]) == 0;
|
||||
}
|
||||
|
||||
findEntity = function(properties, searchRadius, filterFn) {
|
||||
var entities = findEntities(properties, searchRadius, filterFn);
|
||||
return entities.length > 0 ? entities[0] : null;
|
||||
|
@ -116,32 +107,30 @@ findEntities = function(properties, searchRadius, filterFn) {
|
|||
return matchedEntities;
|
||||
}
|
||||
|
||||
function setControllerPartsVisible(parts) {
|
||||
Messages.sendLocalMessage('Controller-Display-Parts', JSON.stringify(parts));
|
||||
function findEntitiesWithTag(tag) {
|
||||
return findEntities({ userData: "" }, 10000, function(properties, key, value) {
|
||||
data = parseJSON(value);
|
||||
return data.tag === tag;
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* A controller in made up of parts, and each part can have multiple "layers,"
|
||||
* which are really just different texures. For example, the "trigger" part
|
||||
* has "normal" and "highlight" layers.
|
||||
*/
|
||||
function setControllerPartLayer(part, layer) {
|
||||
data = {};
|
||||
data[part] = layer;
|
||||
Messages.sendLocalMessage('Controller-Set-Part-Layer', JSON.stringify(data));
|
||||
}
|
||||
|
||||
function triggerHapticPulse() {
|
||||
function scheduleHaptics(delay, strength, duration) {
|
||||
Script.setTimeout(function() {
|
||||
Controller.triggerHapticPulse(strength, duration, 0);
|
||||
Controller.triggerHapticPulse(strength, duration, 1);
|
||||
}, delay);
|
||||
}
|
||||
scheduleHaptics(0, 0.8, 100);
|
||||
scheduleHaptics(300, 0.5, 100);
|
||||
scheduleHaptics(600, 0.3, 100);
|
||||
scheduleHaptics(900, 0.2, 100);
|
||||
scheduleHaptics(1200, 0.1, 100);
|
||||
}
|
||||
|
||||
function spawn(entityData, transform, modifyFn) {
|
||||
debug("Creating: ", entityData);
|
||||
/**
|
||||
* Spawn entities and return the newly created entity's ids.
|
||||
* @param {object[]} entityPropertiesList A list of properties of the entities
|
||||
* to spawn.
|
||||
*/
|
||||
function spawn(entityPropertiesList, transform, modifyFn) {
|
||||
if (!transform) {
|
||||
transform = {
|
||||
position: { x: 0, y: 0, z: 0 },
|
||||
|
@ -149,9 +138,8 @@ function spawn(entityData, transform, modifyFn) {
|
|||
}
|
||||
}
|
||||
var ids = [];
|
||||
for (var i = 0; i < entityData.length; ++i) {
|
||||
var data = entityData[i];
|
||||
debug("Creating: ", data.name);
|
||||
for (var i = 0; i < entityPropertiesList.length; ++i) {
|
||||
var data = entityPropertiesList[i];
|
||||
data.position = Vec3.sum(transform.position, data.position);
|
||||
data.rotation = Quat.multiply(data.rotation, transform.rotation);
|
||||
if (modifyFn) {
|
||||
|
@ -159,11 +147,16 @@ function spawn(entityData, transform, modifyFn) {
|
|||
}
|
||||
var id = Entities.addEntity(data);
|
||||
ids.push(id);
|
||||
debug(id, "data:", JSON.stringify(data));
|
||||
}
|
||||
return ids;
|
||||
}
|
||||
|
||||
/**
|
||||
* @function parseJSON
|
||||
* @param {string} jsonString The string to parse.
|
||||
* @return {object} Return an empty if the string was not valid JSON, otherwise
|
||||
* the parsed object is returned.
|
||||
*/
|
||||
function parseJSON(jsonString) {
|
||||
var data;
|
||||
try {
|
||||
|
@ -174,6 +167,10 @@ function parseJSON(jsonString) {
|
|||
return data;
|
||||
}
|
||||
|
||||
/**
|
||||
* Spawn entities with `tag` in the userData.
|
||||
* @function spawnWithTag
|
||||
*/
|
||||
function spawnWithTag(entityData, transform, tag) {
|
||||
function modifyFn(data) {
|
||||
var userData = parseJSON(data.userData);
|
||||
|
@ -185,6 +182,10 @@ function spawnWithTag(entityData, transform, tag) {
|
|||
return spawn(entityData, transform, modifyFn);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete all entities with the tag `tag` in their userData.
|
||||
* @function deleteEntitiesWithTag
|
||||
*/
|
||||
function deleteEntitiesWithTag(tag) {
|
||||
debug("searching for...:", tag);
|
||||
var entityIDs = findEntitiesWithTag(tag);
|
||||
|
@ -192,6 +193,7 @@ function deleteEntitiesWithTag(tag) {
|
|||
Entities.deleteEntity(entityIDs[i]);
|
||||
}
|
||||
}
|
||||
|
||||
function editEntitiesWithTag(tag, propertiesOrFn) {
|
||||
var entities = TUTORIAL_TAG_TO_ENTITY_IDS_MAP[tag];
|
||||
|
||||
|
@ -208,19 +210,130 @@ function editEntitiesWithTag(tag, propertiesOrFn) {
|
|||
}
|
||||
}
|
||||
|
||||
function findEntitiesWithTag(tag) {
|
||||
return findEntities({ userData: "" }, 10000, function(properties, key, value) {
|
||||
data = parseJSON(value);
|
||||
return data.tag == tag;
|
||||
});
|
||||
}
|
||||
|
||||
// From http://stackoverflow.com/questions/5999998/how-can-i-check-if-a-javascript-variable-is-function-type
|
||||
function isFunction(functionToCheck) {
|
||||
var getType = {};
|
||||
return functionToCheck && getType.toString.call(functionToCheck) === '[object Function]';
|
||||
}
|
||||
|
||||
/**
|
||||
* Return `true` if `entityID` can be found in the local entity tree, otherwise `false`.
|
||||
*/
|
||||
function isEntityInLocalTree(entityID) {
|
||||
return Entities.getEntityProperties(entityID, 'visible').visible !== undefined;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
function showEntitiesWithTags(tags) {
|
||||
for (var i = 0; i < tags.length; ++i) {
|
||||
showEntitiesWithTag(tags[i]);
|
||||
}
|
||||
}
|
||||
|
||||
function showEntitiesWithTag(tag) {
|
||||
var entities = TUTORIAL_TAG_TO_ENTITY_IDS_MAP[tag];
|
||||
if (entities) {
|
||||
for (entityID in entities) {
|
||||
var data = entities[entityID];
|
||||
|
||||
var collisionless = data.visible === false ? true : false;
|
||||
if (data.collidable !== undefined) {
|
||||
collisionless = data.collidable === true ? false : true;
|
||||
}
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = true;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: data.visible == false ? false : true,
|
||||
collisionless: collisionless,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
debug("Showing: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
}
|
||||
} else {
|
||||
debug("ERROR | No entities for tag: ", tag);
|
||||
}
|
||||
|
||||
return;
|
||||
// Dynamic method, suppressed for now
|
||||
//editEntitiesWithTag(tag, function(entityID) {
|
||||
// var userData = Entities.getEntityProperties(entityID, "userData").userData;
|
||||
// var data = parseJSON(userData);
|
||||
// var collisionless = data.visible === false ? true : false;
|
||||
// if (data.collidable !== undefined) {
|
||||
// collisionless = data.collidable === true ? false : true;
|
||||
// }
|
||||
// if (data.soundKey) {
|
||||
// data.soundKey.playing = true;
|
||||
// }
|
||||
// var newProperties = {
|
||||
// visible: data.visible == false ? false : true,
|
||||
// collisionless: collisionless,
|
||||
// userData: JSON.stringify(data),
|
||||
// };
|
||||
// Entities.editEntity(entityID, newProperties);
|
||||
//});
|
||||
}
|
||||
|
||||
function hideEntitiesWithTags(tags) {
|
||||
for (var i = 0; i < tags.length; ++i) {
|
||||
hideEntitiesWithTag(tags[i]);
|
||||
}
|
||||
}
|
||||
|
||||
function hideEntitiesWithTag(tag) {
|
||||
var entities = TUTORIAL_TAG_TO_ENTITY_IDS_MAP[tag];
|
||||
if (entities) {
|
||||
for (entityID in entities) {
|
||||
var data = entities[entityID];
|
||||
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = false;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: false,
|
||||
collisionless: 1,
|
||||
ignoreForCollisions: 1,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
|
||||
debug("Hiding: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
// Dynamic method, suppressed for now
|
||||
//editEntitiesWithTag(tag, function(entityID) {
|
||||
// var userData = Entities.getEntityProperties(entityID, "userData").userData;
|
||||
// var data = parseJSON(userData);
|
||||
// if (data.soundKey) {
|
||||
// data.soundKey.playing = false;
|
||||
// }
|
||||
// var newProperties = {
|
||||
// visible: false,
|
||||
// collisionless: 1,
|
||||
// ignoreForCollisions: 1,
|
||||
// userData: JSON.stringify(data),
|
||||
// };
|
||||
// Entities.editEntity(entityID, newProperties);
|
||||
//});
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the entity properties for an entity with a given name if it is in our
|
||||
* cached list of entities. Otherwise, return undefined.
|
||||
*/
|
||||
function getEntityWithName(name) {
|
||||
debug("Getting entity with name:", name);
|
||||
var entityID = TUTORIAL_NAME_TO_ENTITY_PROPERTIES_MAP[name];
|
||||
debug("Entity id: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
return entityID;
|
||||
}
|
||||
|
||||
function playSuccessSound() {
|
||||
Audio.playSound(successSound, {
|
||||
position: MyAvatar.position,
|
||||
|
@ -229,7 +342,6 @@ function playSuccessSound() {
|
|||
});
|
||||
}
|
||||
|
||||
|
||||
function playFirecrackerSound(position) {
|
||||
Audio.playSound(firecrackerSound, {
|
||||
position: position,
|
||||
|
@ -238,27 +350,17 @@ function playFirecrackerSound(position) {
|
|||
});
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// //
|
||||
// STEP: DISABLE CONTROLLERS //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepStart = function(name) {
|
||||
this.tag = name;
|
||||
}
|
||||
stepStart.prototype = {
|
||||
start: function(onFinish) {
|
||||
disableEverything();
|
||||
|
||||
HMD.requestShowHandControllers();
|
||||
|
||||
onFinish();
|
||||
},
|
||||
cleanup: function() {
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* This disables everything, including:
|
||||
*
|
||||
* - The door to leave the tutorial
|
||||
* - Overlays
|
||||
* - Hand controlelrs
|
||||
* - Teleportation
|
||||
* - Advanced movement
|
||||
* - Equip and far grab
|
||||
* - Away mode
|
||||
*/
|
||||
function disableEverything() {
|
||||
editEntitiesWithTag('door', { visible: true, collisionless: false });
|
||||
Menu.setIsOptionChecked("Overlays", false);
|
||||
|
@ -271,6 +373,11 @@ function disableEverything() {
|
|||
farGrabEnabled: false,
|
||||
}));
|
||||
setControllerPartLayer('touchpad', 'blank');
|
||||
setControllerPartLayer('trigger', 'blank');
|
||||
setControllerPartLayer('joystick', 'blank');
|
||||
setControllerPartLayer('grip', 'blank');
|
||||
setControllerPartLayer('button_a', 'blank');
|
||||
setControllerPartLayer('button_b', 'blank');
|
||||
setControllerPartLayer('tips', 'blank');
|
||||
|
||||
hideEntitiesWithTag('finish');
|
||||
|
@ -278,6 +385,10 @@ function disableEverything() {
|
|||
setAwayEnabled(false);
|
||||
}
|
||||
|
||||
/**
|
||||
* This reenables everything that disableEverything() disables. This can be
|
||||
* used when leaving the tutorial to ensure that nothing is left disabled.
|
||||
*/
|
||||
function reenableEverything() {
|
||||
editEntitiesWithTag('door', { visible: false, collisionless: true });
|
||||
Menu.setIsOptionChecked("Overlays", true);
|
||||
|
@ -290,11 +401,39 @@ function reenableEverything() {
|
|||
farGrabEnabled: true,
|
||||
}));
|
||||
setControllerPartLayer('touchpad', 'blank');
|
||||
setControllerPartLayer('trigger', 'blank');
|
||||
setControllerPartLayer('joystick', 'blank');
|
||||
setControllerPartLayer('grip', 'blank');
|
||||
setControllerPartLayer('button_a', 'blank');
|
||||
setControllerPartLayer('button_b', 'blank');
|
||||
setControllerPartLayer('tips', 'blank');
|
||||
MyAvatar.shouldRenderLocally = true;
|
||||
setAwayEnabled(true);
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// //
|
||||
// STEP: DISABLE CONTROLLERS //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepStart = function() {
|
||||
this.name = 'start';
|
||||
};
|
||||
stepStart.prototype = {
|
||||
start: function(onFinish) {
|
||||
disableEverything();
|
||||
|
||||
HMD.requestShowHandControllers();
|
||||
|
||||
onFinish();
|
||||
},
|
||||
cleanup: function() {
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// //
|
||||
|
@ -302,10 +441,9 @@ function reenableEverything() {
|
|||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
var stepEnableControllers = function(name) {
|
||||
this.tag = name;
|
||||
var stepEnableControllers = function() {
|
||||
this.shouldLog = false;
|
||||
}
|
||||
};
|
||||
stepEnableControllers.prototype = {
|
||||
start: function(onFinish) {
|
||||
reenableEverything();
|
||||
|
@ -316,28 +454,6 @@ stepEnableControllers.prototype = {
|
|||
}
|
||||
};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
// //
|
||||
// STEP: Welcome //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepWelcome = function(name) {
|
||||
this.tag = name;
|
||||
}
|
||||
stepWelcome.prototype = {
|
||||
start: function(onFinish) {
|
||||
this.timerID = Script.setTimeout(onFinish, 8000);
|
||||
showEntitiesWithTag(this.tag);
|
||||
},
|
||||
cleanup: function() {
|
||||
if (this.timerID) {
|
||||
Script.clearTimeout(this.timerID);
|
||||
this.timerID = null;
|
||||
}
|
||||
hideEntitiesWithTag(this.tag);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -346,9 +462,9 @@ stepWelcome.prototype = {
|
|||
// STEP: Orient and raise hands above head //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepOrient = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepOrient = function(tutorialManager) {
|
||||
this.name = 'orient';
|
||||
this.tags = ["orient", "orient-" + tutorialManager.controllerName];
|
||||
}
|
||||
stepOrient.prototype = {
|
||||
start: function(onFinish) {
|
||||
|
@ -357,7 +473,8 @@ stepOrient.prototype = {
|
|||
var tag = this.tag;
|
||||
|
||||
// Spawn content set
|
||||
editEntitiesWithTag(this.tag, { visible: true });
|
||||
//editEntitiesWithTag(this.tag, { visible: true });
|
||||
showEntitiesWithTags(this.tags);
|
||||
|
||||
this.checkIntervalID = null;
|
||||
function checkForHandsAboveHead() {
|
||||
|
@ -386,8 +503,8 @@ stepOrient.prototype = {
|
|||
Script.clearInterval(this.checkIntervalID);
|
||||
this.checkIntervalID = null;
|
||||
}
|
||||
editEntitiesWithTag(this.tag, { visible: false, collisionless: 1 });
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
//editEntitiesWithTag(this.tag, { visible: false, collisionless: 1 });
|
||||
hideEntitiesWithTags(this.tags);
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -399,9 +516,10 @@ stepOrient.prototype = {
|
|||
// STEP: Near Grab //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepNearGrab = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepNearGrab = function() {
|
||||
this.name = 'nearGrab';
|
||||
this.tag = "nearGrab";
|
||||
this.tempTag = "nearGrab-temporary";
|
||||
this.birdIDs = [];
|
||||
|
||||
Messages.subscribe("Entity-Exploded");
|
||||
|
@ -414,7 +532,6 @@ stepNearGrab.prototype = {
|
|||
|
||||
setControllerPartLayer('tips', 'trigger');
|
||||
setControllerPartLayer('trigger', 'highlight');
|
||||
var tag = this.tag;
|
||||
|
||||
// Spawn content set
|
||||
showEntitiesWithTag(this.tag, { visible: true });
|
||||
|
@ -457,6 +574,7 @@ stepNearGrab.prototype = {
|
|||
setControllerPartLayer('tips', 'blank');
|
||||
setControllerPartLayer('trigger', 'normal');
|
||||
hideEntitiesWithTag(this.tag, { visible: false});
|
||||
hideEntitiesWithTag('bothGrab', { visible: false});
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
if (this.positionWatcher) {
|
||||
this.positionWatcher.destroy();
|
||||
|
@ -473,9 +591,10 @@ stepNearGrab.prototype = {
|
|||
// STEP: Far Grab //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepFarGrab = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepFarGrab = function() {
|
||||
this.name = 'farGrab';
|
||||
this.tag = "farGrab";
|
||||
this.tempTag = "farGrab-temporary";
|
||||
this.finished = true;
|
||||
this.birdIDs = [];
|
||||
|
||||
|
@ -535,7 +654,6 @@ stepFarGrab.prototype = {
|
|||
setControllerPartLayer('tips', 'blank');
|
||||
setControllerPartLayer('trigger', 'normal');
|
||||
hideEntitiesWithTag(this.tag, { visible: false});
|
||||
hideEntitiesWithTag('bothGrab', { visible: false});
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
if (this.positionWatcher) {
|
||||
this.positionWatcher.destroy();
|
||||
|
@ -576,11 +694,16 @@ PositionWatcher.prototype = {
|
|||
// STEP: Equip //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepEquip = function(name) {
|
||||
this.tag = name;
|
||||
this.tagPart1 = name + "-part1";
|
||||
this.tagPart2 = name + "-part2";
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepEquip = function(tutorialManager) {
|
||||
const controllerName = tutorialManager.controllerName;
|
||||
|
||||
this.name = 'equip';
|
||||
|
||||
this.tags = ["equip", "equip-" + controllerName];
|
||||
this.tagsPart1 = ["equip-part1", "equip-part1-" + controllerName];
|
||||
this.tagsPart2 = ["equip-part2", "equip-part2-" + controllerName];
|
||||
this.tempTag = "equip-temporary";
|
||||
|
||||
this.PART1 = 0;
|
||||
this.PART2 = 1;
|
||||
this.PART3 = 2;
|
||||
|
@ -593,6 +716,7 @@ stepEquip.prototype = {
|
|||
start: function(onFinish) {
|
||||
setControllerPartLayer('tips', 'trigger');
|
||||
setControllerPartLayer('trigger', 'highlight');
|
||||
|
||||
Messages.sendLocalMessage('Hifi-Grab-Disable', JSON.stringify({
|
||||
holdEnabled: true,
|
||||
}));
|
||||
|
@ -600,8 +724,8 @@ stepEquip.prototype = {
|
|||
var tag = this.tag;
|
||||
|
||||
// Spawn content set
|
||||
showEntitiesWithTag(this.tag);
|
||||
showEntitiesWithTag(this.tagPart1);
|
||||
showEntitiesWithTags(this.tags);
|
||||
showEntitiesWithTags(this.tagsPart1);
|
||||
|
||||
this.currentPart = this.PART1;
|
||||
|
||||
|
@ -658,9 +782,10 @@ stepEquip.prototype = {
|
|||
Script.setTimeout(function() {
|
||||
debug("Equip | Starting part 3");
|
||||
this.currentPart = this.PART3;
|
||||
hideEntitiesWithTag(this.tagPart1);
|
||||
showEntitiesWithTag(this.tagPart2);
|
||||
hideEntitiesWithTags(this.tagsPart1);
|
||||
showEntitiesWithTags(this.tagsPart2);
|
||||
setControllerPartLayer('trigger', 'normal');
|
||||
setControllerPartLayer('grip', 'highlight');
|
||||
setControllerPartLayer('tips', 'grip');
|
||||
Messages.subscribe('Hifi-Object-Manipulation');
|
||||
debug("Equip | Finished starting part 3");
|
||||
|
@ -687,16 +812,19 @@ stepEquip.prototype = {
|
|||
}
|
||||
|
||||
setControllerPartLayer('tips', 'blank');
|
||||
setControllerPartLayer('grip', 'normal');
|
||||
setControllerPartLayer('trigger', 'normal');
|
||||
this.stopWatchingGun();
|
||||
this.currentPart = this.COMPLETE;
|
||||
|
||||
if (this.checkCollidesTimer) {
|
||||
Script.clearInterval(this.checkCollidesTimer);
|
||||
this.checkColllidesTimer = null;
|
||||
}
|
||||
hideEntitiesWithTag(this.tagPart1);
|
||||
hideEntitiesWithTag(this.tagPart2);
|
||||
hideEntitiesWithTag(this.tag);
|
||||
|
||||
hideEntitiesWithTags(this.tagsPart1);
|
||||
hideEntitiesWithTags(this.tagsPart2);
|
||||
hideEntitiesWithTags(this.tags);
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
}
|
||||
};
|
||||
|
@ -710,9 +838,11 @@ stepEquip.prototype = {
|
|||
// STEP: Turn Around //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepTurnAround = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepTurnAround = function(tutorialManager) {
|
||||
this.name = 'turnAround';
|
||||
|
||||
this.tags = ["turnAround", "turnAround-" + tutorialManager.controllerName];
|
||||
this.tempTag = "turnAround-temporary";
|
||||
|
||||
this.onActionBound = this.onAction.bind(this);
|
||||
this.numTimesSnapTurnPressed = 0;
|
||||
|
@ -720,10 +850,11 @@ var stepTurnAround = function(name) {
|
|||
}
|
||||
stepTurnAround.prototype = {
|
||||
start: function(onFinish) {
|
||||
setControllerPartLayer('joystick', 'highlight');
|
||||
setControllerPartLayer('touchpad', 'arrows');
|
||||
setControllerPartLayer('tips', 'arrows');
|
||||
|
||||
showEntitiesWithTag(this.tag);
|
||||
showEntitiesWithTags(this.tags);
|
||||
|
||||
this.numTimesSnapTurnPressed = 0;
|
||||
this.numTimesSmoothTurnPressed = 0;
|
||||
|
@ -776,13 +907,14 @@ stepTurnAround.prototype = {
|
|||
} catch (e) {
|
||||
}
|
||||
|
||||
setControllerPartLayer('joystick', 'normal');
|
||||
setControllerPartLayer('touchpad', 'blank');
|
||||
setControllerPartLayer('tips', 'blank');
|
||||
|
||||
if (this.interval) {
|
||||
Script.clearInterval(this.interval);
|
||||
}
|
||||
hideEntitiesWithTag(this.tag);
|
||||
hideEntitiesWithTags(this.tags);
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
}
|
||||
};
|
||||
|
@ -796,12 +928,15 @@ stepTurnAround.prototype = {
|
|||
// STEP: Teleport //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepTeleport = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepTeleport = function(tutorialManager) {
|
||||
this.name = 'teleport';
|
||||
|
||||
this.tags = ["teleport", "teleport-" + tutorialManager.controllerName];
|
||||
this.tempTag = "teleport-temporary";
|
||||
}
|
||||
stepTeleport.prototype = {
|
||||
start: function(onFinish) {
|
||||
setControllerPartLayer('button_a', 'highlight');
|
||||
setControllerPartLayer('touchpad', 'teleport');
|
||||
setControllerPartLayer('tips', 'teleport');
|
||||
|
||||
|
@ -831,17 +966,18 @@ stepTeleport.prototype = {
|
|||
}
|
||||
this.checkCollidesTimer = Script.setInterval(checkCollides.bind(this), 500);
|
||||
|
||||
showEntitiesWithTag(this.tag);
|
||||
showEntitiesWithTags(this.tags);
|
||||
},
|
||||
cleanup: function() {
|
||||
debug("Teleport | Cleanup");
|
||||
setControllerPartLayer('button_a', 'normal');
|
||||
setControllerPartLayer('touchpad', 'blank');
|
||||
setControllerPartLayer('tips', 'blank');
|
||||
|
||||
if (this.checkCollidesTimer) {
|
||||
Script.clearInterval(this.checkCollidesTimer);
|
||||
}
|
||||
hideEntitiesWithTag(this.tag);
|
||||
hideEntitiesWithTags(this.tags);
|
||||
deleteEntitiesWithTag(this.tempTag);
|
||||
}
|
||||
};
|
||||
|
@ -856,9 +992,11 @@ stepTeleport.prototype = {
|
|||
// STEP: Finish //
|
||||
// //
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
var stepFinish = function(name) {
|
||||
this.tag = name;
|
||||
this.tempTag = name + "-temporary";
|
||||
var stepFinish = function() {
|
||||
this.name = 'finish';
|
||||
|
||||
this.tag = "finish";
|
||||
this.tempTag = "finish-temporary";
|
||||
}
|
||||
stepFinish.prototype = {
|
||||
start: function(onFinish) {
|
||||
|
@ -872,6 +1010,8 @@ stepFinish.prototype = {
|
|||
};
|
||||
|
||||
var stepCleanupFinish = function() {
|
||||
this.name = 'cleanup';
|
||||
|
||||
this.shouldLog = false;
|
||||
}
|
||||
stepCleanupFinish.prototype = {
|
||||
|
@ -885,101 +1025,6 @@ stepCleanupFinish.prototype = {
|
|||
|
||||
|
||||
|
||||
function isEntityInLocalTree(entityID) {
|
||||
return Entities.getEntityProperties(entityID, 'visible').visible !== undefined;
|
||||
}
|
||||
|
||||
function showEntitiesWithTag(tag) {
|
||||
var entities = TUTORIAL_TAG_TO_ENTITY_IDS_MAP[tag];
|
||||
if (entities) {
|
||||
for (entityID in entities) {
|
||||
var data = entities[entityID];
|
||||
|
||||
var collisionless = data.visible === false ? true : false;
|
||||
if (data.collidable !== undefined) {
|
||||
collisionless = data.collidable === true ? false : true;
|
||||
}
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = true;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: data.visible == false ? false : true,
|
||||
collisionless: collisionless,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
debug("Showing: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
}
|
||||
}
|
||||
|
||||
// Dynamic method, suppressed for now
|
||||
return;
|
||||
editEntitiesWithTag(tag, function(entityID) {
|
||||
var userData = Entities.getEntityProperties(entityID, "userData").userData;
|
||||
var data = parseJSON(userData);
|
||||
var collisionless = data.visible === false ? true : false;
|
||||
if (data.collidable !== undefined) {
|
||||
collisionless = data.collidable === true ? false : true;
|
||||
}
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = true;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: data.visible == false ? false : true,
|
||||
collisionless: collisionless,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
});
|
||||
}
|
||||
|
||||
function hideEntitiesWithTag(tag) {
|
||||
var entities = TUTORIAL_TAG_TO_ENTITY_IDS_MAP[tag];
|
||||
if (entities) {
|
||||
for (entityID in entities) {
|
||||
var data = entities[entityID];
|
||||
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = false;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: false,
|
||||
collisionless: 1,
|
||||
ignoreForCollisions: 1,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
|
||||
debug("Hiding: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
}
|
||||
}
|
||||
|
||||
// Dynamic method, suppressed for now
|
||||
return;
|
||||
editEntitiesWithTag(tag, function(entityID) {
|
||||
var userData = Entities.getEntityProperties(entityID, "userData").userData;
|
||||
var data = parseJSON(userData);
|
||||
if (data.soundKey) {
|
||||
data.soundKey.playing = false;
|
||||
}
|
||||
var newProperties = {
|
||||
visible: false,
|
||||
collisionless: 1,
|
||||
ignoreForCollisions: 1,
|
||||
userData: JSON.stringify(data),
|
||||
};
|
||||
Entities.editEntity(entityID, newProperties);
|
||||
});
|
||||
}
|
||||
|
||||
// Return the entity properties for an entity with a given name if it is in our
|
||||
// cached list of entities. Otherwise, return undefined.
|
||||
function getEntityWithName(name) {
|
||||
debug("Getting entity with name:", name);
|
||||
var entityID = TUTORIAL_NAME_TO_ENTITY_PROPERTIES_MAP[name];
|
||||
debug("Entity id: ", entityID, ", Is in local tree: ", isEntityInLocalTree(entityID));
|
||||
return entityID;
|
||||
}
|
||||
|
||||
|
||||
TutorialManager = function() {
|
||||
|
@ -992,11 +1037,25 @@ TutorialManager = function() {
|
|||
var didFinishTutorial = false;
|
||||
|
||||
var wentToEntryStepNum;
|
||||
var VERSION = 1;
|
||||
var VERSION = 2;
|
||||
var tutorialID;
|
||||
|
||||
var self = this;
|
||||
|
||||
// The real controller name is the actual detected controller name, or 'unknown'
|
||||
// if one is not found.
|
||||
if (HMD.isSubdeviceContainingNameAvailable("OculusTouch")) {
|
||||
this.controllerName = "touch";
|
||||
this.realControllerName = "touch";
|
||||
} else if (HMD.isHandControllerAvailable("OpenVR")) {
|
||||
this.controllerName = "vive";
|
||||
this.realControllerName = "vive";
|
||||
} else {
|
||||
info("ERROR, no known hand controller found, defaulting to Vive");
|
||||
this.controllerName = "vive";
|
||||
this.realControllerName = "unknown";
|
||||
}
|
||||
|
||||
this.startTutorial = function() {
|
||||
currentStepNum = -1;
|
||||
currentStep = null;
|
||||
|
@ -1006,15 +1065,15 @@ TutorialManager = function() {
|
|||
// If Script.generateUUID is not available, default to an empty string.
|
||||
tutorialID = Script.generateUUID ? Script.generateUUID() : "";
|
||||
STEPS = [
|
||||
new stepStart("start"),
|
||||
new stepOrient("orient"),
|
||||
new stepNearGrab("nearGrab"),
|
||||
new stepFarGrab("farGrab"),
|
||||
new stepEquip("equip"),
|
||||
new stepTurnAround("turnAround"),
|
||||
new stepTeleport("teleport"),
|
||||
new stepFinish("finish"),
|
||||
new stepEnableControllers("enableControllers"),
|
||||
new stepStart(this),
|
||||
new stepOrient(this),
|
||||
new stepFarGrab(this),
|
||||
new stepNearGrab(this),
|
||||
new stepEquip(this),
|
||||
new stepTurnAround(this),
|
||||
new stepTeleport(this),
|
||||
new stepFinish(this),
|
||||
new stepEnableControllers(this),
|
||||
];
|
||||
wentToEntryStepNum = STEPS.length;
|
||||
for (var i = 0; i < STEPS.length; ++i) {
|
||||
|
@ -1027,7 +1086,7 @@ TutorialManager = function() {
|
|||
this.onFinish = function() {
|
||||
debug("onFinish", currentStepNum);
|
||||
if (currentStep && currentStep.shouldLog !== false) {
|
||||
self.trackStep(currentStep.tag, currentStepNum);
|
||||
self.trackStep(currentStep.name, currentStepNum);
|
||||
}
|
||||
|
||||
self.startNextStep();
|
||||
|
@ -1083,7 +1142,7 @@ TutorialManager = function() {
|
|||
var tutorialTimeElapsed = (Date.now() - startedTutorialAt) / 1000;
|
||||
UserActivityLogger.tutorialProgress(
|
||||
name, stepNum, timeToFinishStep, tutorialTimeElapsed,
|
||||
tutorialID, VERSION);
|
||||
tutorialID, VERSION, this.realControllerName);
|
||||
}
|
||||
|
||||
// This is a message sent from the "entry" portal in the courtyard,
|
||||
|
@ -1099,6 +1158,25 @@ TutorialManager = function() {
|
|||
|
||||
// To run the tutorial:
|
||||
//
|
||||
// var tutorialManager = new TutorialManager();
|
||||
// tutorialManager.startTutorial();
|
||||
//var tutorialManager = new TutorialManager();
|
||||
//tutorialManager.startTutorial();
|
||||
//
|
||||
//
|
||||
//var keyReleaseHandler = function(event) {
|
||||
// if (event.isShifted && event.isAlt) {
|
||||
// print('here', event.text);
|
||||
// if (event.text == "F12") {
|
||||
// if (!tutorialManager.startNextStep()) {
|
||||
// tutorialManager.startTutorial();
|
||||
// }
|
||||
// } else if (event.text == "F11") {
|
||||
// tutorialManager.restartStep();
|
||||
// } else if (event.text == "F10") {
|
||||
// MyAvatar.shouldRenderLocally = !MyAvatar.shouldRenderLocally;
|
||||
// } else if (event.text == "r") {
|
||||
// tutorialManager.stopTutorial();
|
||||
// tutorialManager.startTutorial();
|
||||
// }
|
||||
// }
|
||||
//};
|
||||
//Controller.keyReleaseEvent.connect(keyReleaseHandler);
|
||||
|
|
|
@ -1,8 +1,25 @@
|
|||
TUTORIAL_TAG_TO_ENTITY_IDS_MAP = {
|
||||
"teleport": {
|
||||
"teleport-vive": {
|
||||
"{7df1abc4-1b7c-4352-985c-f3f6ad8d65b7}": {
|
||||
"tag": "teleport-vive"
|
||||
}
|
||||
},
|
||||
"teleport-touch": {
|
||||
"{ff064b9e-7fa4-4693-a386-a67b9f92a948}": {
|
||||
"tag": "teleport"
|
||||
},
|
||||
"tag": "teleport-touch"
|
||||
}
|
||||
},
|
||||
"turnAround-vive": {
|
||||
"{9b14f224-b2f6-447f-bb86-f5d875cf4c33}": {
|
||||
"tag": "turnAround-vive"
|
||||
}
|
||||
},
|
||||
"turnAround-touch": {
|
||||
"{ce74b3ca-d1c7-4980-bd98-2d488095a39e}": {
|
||||
"tag": "turnAround-touch"
|
||||
}
|
||||
},
|
||||
"teleport": {
|
||||
"{4478f7b5-d3ac-4213-9a7b-ad8cd69575b8}": {
|
||||
"tag": "teleport"
|
||||
}
|
||||
|
@ -82,17 +99,19 @@ TUTORIAL_TAG_TO_ENTITY_IDS_MAP = {
|
|||
"tag": "equip-part1"
|
||||
}
|
||||
},
|
||||
"equip-part2": {
|
||||
"equip-part2-vive": {
|
||||
"{b5d17eda-90ab-40cf-b973-efcecb2e992e}": {
|
||||
"tag": "equip-part2"
|
||||
},
|
||||
"{6307cd16-dd1d-4988-a339-578178436b45}": {
|
||||
"tag": "equip-part2"
|
||||
"tag": "equip-part2-vive"
|
||||
}
|
||||
},
|
||||
"turnAround": {
|
||||
"{ce74b3ca-d1c7-4980-bd98-2d488095a39e}": {
|
||||
"tag": "turnAround"
|
||||
"equip-part2-touch": {
|
||||
"{69195139-e020-4739-bb2c-50faebc6860a}": {
|
||||
"tag": "equip-part2-touch"
|
||||
}
|
||||
},
|
||||
"equip-part2": {
|
||||
"{6307cd16-dd1d-4988-a339-578178436b45}": {
|
||||
"tag": "equip-part2"
|
||||
}
|
||||
},
|
||||
"bothGrab": {
|
||||
|
@ -143,133 +162,144 @@ TUTORIAL_TAG_TO_ENTITY_IDS_MAP = {
|
|||
"tag": "equip"
|
||||
}
|
||||
},
|
||||
"orient": {
|
||||
"orient-vive": {
|
||||
"{95d233ab-ed0a-46e1-b047-1c542688ef3f}": {
|
||||
"tag": "orient"
|
||||
"tag": "orient-vive"
|
||||
}
|
||||
},
|
||||
"orient-touch": {
|
||||
"{1c95f945-ec46-4aac-b0f1-e64e073dbfaa}": {
|
||||
"tag": "orient-touch"
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
TUTORIAL_NAME_TO_ENTITY_PROPERTIES_MAP = {
|
||||
"tutorial/gun_spawn": {
|
||||
"userData": "{\"tag\":\"equip\",\"visible\":false}",
|
||||
"dimensions": {
|
||||
"y": 0.0649842768907547,
|
||||
"x": 0.0649842768907547,
|
||||
"z": 0.0649842768907547
|
||||
},
|
||||
"clientOnly": 0,
|
||||
"collisionless": 1,
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"color": {
|
||||
"blue": 0,
|
||||
"green": 0,
|
||||
"red": 255
|
||||
},
|
||||
"queryAACube": {
|
||||
"y": 0.6283726096153259,
|
||||
"x": 0.6865367293357849,
|
||||
"scale": 0.11255607008934021,
|
||||
"z": 0.3359576463699341
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"dimensions": {
|
||||
"x": 0.0649842768907547,
|
||||
"y": 0.0649842768907547,
|
||||
"z": 0.0649842768907547
|
||||
},
|
||||
"visible": 0,
|
||||
"shape": "Cube",
|
||||
"clientOnly": 0,
|
||||
"id": "{9df518da-9e65-4b76-8a79-eeefdb0b7310}",
|
||||
"ignoreForCollisions": 1,
|
||||
"lastEdited": 1481926907366120,
|
||||
"lastEditedBy": "{b80185ea-0936-4397-a5a4-3a64004f545f}",
|
||||
"name": "tutorial/gun_spawn",
|
||||
"owningAvatarID": "{00000000-0000-0000-0000-000000000000}",
|
||||
"position": {
|
||||
"y": 0.6846506595611572,
|
||||
"x": 0.7428147792816162,
|
||||
"z": 0.3922356963157654
|
||||
"x": 0.60231781005859375,
|
||||
"y": 0.68465065956115723,
|
||||
"z": 0.39223569631576538
|
||||
},
|
||||
"queryAACube": {
|
||||
"scale": 0.11255607008934021,
|
||||
"x": 0.54603976011276245,
|
||||
"y": 0.62837260961532593,
|
||||
"z": 0.33595764636993408
|
||||
},
|
||||
"rotation": {
|
||||
"y": 0.7066605091094971,
|
||||
"x": 0.7066605091094971,
|
||||
"z": -0.025131583213806152,
|
||||
"w": -0.025101065635681152
|
||||
"w": -0.025101065635681152,
|
||||
"x": 0.70666050910949707,
|
||||
"y": 0.70666050910949707,
|
||||
"z": -0.025131583213806152
|
||||
},
|
||||
"ignoreForCollisions": 1,
|
||||
"shape": "Cube",
|
||||
"type": "Box",
|
||||
"id": "{9df518da-9e65-4b76-8a79-eeefdb0b7310}",
|
||||
"name": "tutorial/gun_spawn"
|
||||
"userData": "{\"visible\":false,\"tag\":\"equip\"}",
|
||||
"visible": 0
|
||||
},
|
||||
"tutorial/nearGrab/box_spawn": {
|
||||
"userData": "{\"tag\":\"nearGrab\",\"visible\":false}",
|
||||
"dimensions": {
|
||||
"y": 0.08225371688604355,
|
||||
"x": 0.08225371688604355,
|
||||
"z": 0.08225371688604355
|
||||
},
|
||||
"clientOnly": 0,
|
||||
"collisionless": 1,
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"color": {
|
||||
"blue": 255,
|
||||
"green": 0,
|
||||
"red": 255
|
||||
},
|
||||
"queryAACube": {
|
||||
"y": 0.738319456577301,
|
||||
"x": 0.8985498547554016,
|
||||
"scale": 0.14246761798858643,
|
||||
"z": 0.29067665338516235
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"dimensions": {
|
||||
"x": 0.082253716886043549,
|
||||
"y": 0.082253716886043549,
|
||||
"z": 0.082253716886043549
|
||||
},
|
||||
"visible": 0,
|
||||
"shape": "Cube",
|
||||
"clientOnly": 0,
|
||||
"id": "{5cf22b9c-fb22-4854-8821-554422980b24}",
|
||||
"ignoreForCollisions": 1,
|
||||
"lastEdited": 1481926907334206,
|
||||
"lastEditedBy": "{b80185ea-0936-4397-a5a4-3a64004f545f}",
|
||||
"name": "tutorial/nearGrab/box_spawn",
|
||||
"owningAvatarID": "{00000000-0000-0000-0000-000000000000}",
|
||||
"position": {
|
||||
"y": 0.8095532655715942,
|
||||
"x": 0.9697836637496948,
|
||||
"x": 0.61857688426971436,
|
||||
"y": 0.80955326557159424,
|
||||
"z": 0.36191046237945557
|
||||
},
|
||||
"rotation": {
|
||||
"y": -1.52587890625e-05,
|
||||
"x": -1.52587890625e-05,
|
||||
"z": -1.52587890625e-05,
|
||||
"w": 1
|
||||
"queryAACube": {
|
||||
"scale": 0.14246761798858643,
|
||||
"x": 0.54734307527542114,
|
||||
"y": 0.73831945657730103,
|
||||
"z": 0.29067665338516235
|
||||
},
|
||||
"ignoreForCollisions": 1,
|
||||
"rotation": {
|
||||
"w": 1,
|
||||
"x": -1.52587890625e-05,
|
||||
"y": -1.52587890625e-05,
|
||||
"z": -1.52587890625e-05
|
||||
},
|
||||
"shape": "Cube",
|
||||
"type": "Box",
|
||||
"id": "{5cf22b9c-fb22-4854-8821-554422980b24}",
|
||||
"name": "tutorial/nearGrab/box_spawn"
|
||||
"userData": "{\"visible\":false,\"tag\":\"nearGrab\"}",
|
||||
"visible": 0
|
||||
},
|
||||
"tutorial/farGrab/box_spawn": {
|
||||
"userData": "{\"tag\":\"farGrab\",\"visible\":false}",
|
||||
"dimensions": {
|
||||
"y": 0.37358683347702026,
|
||||
"x": 0.37358683347702026,
|
||||
"z": 0.37358683347702026
|
||||
},
|
||||
"clientOnly": 0,
|
||||
"collisionless": 1,
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"color": {
|
||||
"blue": 255,
|
||||
"green": 0,
|
||||
"red": 255
|
||||
},
|
||||
"queryAACube": {
|
||||
"y": 0.3304251432418823,
|
||||
"x": 3.0951309204101562,
|
||||
"scale": 0.647071361541748,
|
||||
"z": 0.18027013540267944
|
||||
"created": "2016-09-08T18:38:24Z",
|
||||
"dimensions": {
|
||||
"x": 0.16850528120994568,
|
||||
"y": 0.16850528120994568,
|
||||
"z": 0.16850528120994568
|
||||
},
|
||||
"visible": 0,
|
||||
"shape": "Cube",
|
||||
"clientOnly": 0,
|
||||
"id": "{70fcd96c-cd59-4f23-9ca5-a167f2f85680}",
|
||||
"ignoreForCollisions": 1,
|
||||
"lastEdited": 1481926908795578,
|
||||
"lastEditedBy": "{b80185ea-0936-4397-a5a4-3a64004f545f}",
|
||||
"name": "tutorial/farGrab/box_spawn",
|
||||
"owningAvatarID": "{00000000-0000-0000-0000-000000000000}",
|
||||
"position": {
|
||||
x: 3.4866,
|
||||
y: 0.6716,
|
||||
z: 0.4789
|
||||
"x": 3.4866282939910889,
|
||||
"y": 0.67159509658813477,
|
||||
"z": 0.47892442345619202
|
||||
},
|
||||
"queryAACube": {
|
||||
"scale": 0.64707136154174805,
|
||||
"x": 3.2037394046783447,
|
||||
"y": 0.33042514324188232,
|
||||
"z": 0.14542555809020996
|
||||
},
|
||||
"rotation": {
|
||||
"y": -1.52587890625e-05,
|
||||
"w": 1,
|
||||
"x": -1.52587890625e-05,
|
||||
"z": -1.52587890625e-05,
|
||||
"w": 1
|
||||
"y": -1.52587890625e-05,
|
||||
"z": -1.52587890625e-05
|
||||
},
|
||||
"ignoreForCollisions": 1,
|
||||
"shape": "Cube",
|
||||
"type": "Box",
|
||||
"id": "{70fcd96c-cd59-4f23-9ca5-a167f2f85680}",
|
||||
"name": "tutorial/farGrab/box_spawn"
|
||||
"userData": "{\"visible\":false,\"tag\":\"farGrab\"}",
|
||||
"visible": 0
|
||||
},
|
||||
"tutorial/teleport/pad": {
|
||||
"userData": "{\"tag\":\"teleport\"}",
|
||||
|
|
|
@ -45,7 +45,7 @@ if (!Function.prototype.bind) {
|
|||
keyReleaseHandler: function(event) {
|
||||
print(event.text);
|
||||
if (event.isShifted && event.isAlt) {
|
||||
if (event.text == ",") {
|
||||
if (event.text == "F12") {
|
||||
if (!this.tutorialManager.startNextStep()) {
|
||||
this.tutorialManager.startTutorial();
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue