mirror of
https://github.com/Armored-Dragon/overte.git
synced 2025-03-11 16:13:16 +01:00
migrating platform plugin
This commit is contained in:
parent
a905310a58
commit
4320f4cbe4
22 changed files with 185 additions and 900 deletions
|
@ -120,6 +120,7 @@
|
|||
#include <plugins/PluginManager.h>
|
||||
#include <plugins/PluginUtils.h>
|
||||
#include <plugins/SteamClientPlugin.h>
|
||||
#include <plugins/OculusPlatformPlugin.h>
|
||||
#include <plugins/InputConfiguration.h>
|
||||
#include <RecordingScriptingInterface.h>
|
||||
#include <render/EngineStats.h>
|
||||
|
@ -5958,8 +5959,8 @@ void Application::update(float deltaTime) {
|
|||
}
|
||||
}
|
||||
|
||||
if (auto oculusPlugin = PluginManager::getInstance()->getOculusDisplayPlugin()) {
|
||||
oculusPlugin->pluginUpdate();
|
||||
if (auto oculusPlugin = PluginManager::getInstance()->getOculusPlatformPlugin()) {
|
||||
oculusPlugin->handleOVREvents();
|
||||
}
|
||||
|
||||
userInputMapper->setInputCalibrationData(calibrationData);
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
|
||||
#include <plugins/PluginManager.h>
|
||||
#include <plugins/SteamClientPlugin.h>
|
||||
#include <plugins/OculusPlatformPlugin.h>
|
||||
#include <shared/GlobalAppProperties.h>
|
||||
#include <ui/TabletScriptingInterface.h>
|
||||
#include <UserActivityLogger.h>
|
||||
|
@ -105,8 +106,8 @@ bool LoginDialog::isSteamRunning() const {
|
|||
}
|
||||
|
||||
bool LoginDialog::isOculusRunning() const {
|
||||
auto oculusDisplay = PluginManager::getInstance()->getOculusDisplayPlugin();
|
||||
return (oculusDisplay != nullptr);
|
||||
auto oculusPlatform = PluginManager::getInstance()->getOculusPlatformPlugin();
|
||||
return (oculusPlatform != nullptr);
|
||||
}
|
||||
|
||||
void LoginDialog::dismissLoginDialog() {
|
||||
|
@ -124,8 +125,8 @@ void LoginDialog::login(const QString& username, const QString& password) const
|
|||
|
||||
void LoginDialog::loginThroughOculus() {
|
||||
qDebug() << "Attempting to login through Oculus";
|
||||
if (auto oculusDisplay = PluginManager::getInstance()->getOculusDisplayPlugin()) {
|
||||
oculusDisplay->requestTicket([this](QString nonce, QString userID) {
|
||||
if (auto oculusPlatform = PluginManager::getInstance()->getOculusPlatformPlugin()) {
|
||||
//oculusPlatform->requestTicket([this](QString nonce, QString userID) {
|
||||
// if (nonce.isEmpty() || userID.isEmpty()) {
|
||||
// emit handleLoginFailed();
|
||||
// return;
|
||||
|
@ -138,8 +139,8 @@ void LoginDialog::loginThroughOculus() {
|
|||
|
||||
void LoginDialog::linkOculus() {
|
||||
qDebug() << "Attempting to link Oculus account";
|
||||
if (auto oculusDisplay = PluginManager::getInstance()->getOculusDisplayPlugin()) {
|
||||
//oculusDisplay->requestTicket([this](QString nonce, QString userID) {
|
||||
if (auto oculusPlatform = PluginManager::getInstance()->getOculusPlatformPlugin()) {
|
||||
//oculusPlatform->requestTicket([this](QString nonce, QString userID) {
|
||||
// if (nonce.isEmpty() || userID.isEmpty()) {
|
||||
// emit handleLoginFailed();
|
||||
// return;
|
||||
|
@ -165,8 +166,8 @@ void LoginDialog::linkOculus() {
|
|||
|
||||
void LoginDialog::createAccountFromOculus(QString username) {
|
||||
qDebug() << "Attempting to create account from Oculus info";
|
||||
if (auto oculusDisplay = PluginManager::getInstance()->getOculusDisplayPlugin()) {
|
||||
//oculusDisplay->requestTicket([this, username](QString nonce, QString userID) {
|
||||
if (auto oculusPlatform = PluginManager::getInstance()->getOculusPlatformPlugin()) {
|
||||
//oculusPlatform->requestTicket([this, username](QString nonce, QString userID) {
|
||||
// if (nonce.isEmpty() || userID.isEmpty()) {
|
||||
// emit handleLoginFailed();
|
||||
// return;
|
||||
|
|
|
@ -21,7 +21,6 @@ class DisplayPlugin;
|
|||
class InputPlugin;
|
||||
class CodecPlugin;
|
||||
class SteamClientPlugin;
|
||||
class OculusDisplayPlugin;
|
||||
class OculusPlatformPlugin;
|
||||
class Plugin;
|
||||
class PluginContainer;
|
||||
|
@ -37,6 +36,5 @@ using CodecPluginPointer = std::shared_ptr<CodecPlugin>;
|
|||
using CodecPluginList = std::vector<CodecPluginPointer>;
|
||||
using CodecPluginProvider = std::function<CodecPluginList()>;
|
||||
using SteamClientPluginPointer = std::shared_ptr<SteamClientPlugin>;
|
||||
using OculusDisplayPluginPointer = std::shared_ptr<OculusDisplayPlugin>;
|
||||
using OculusPlatformPluginPointer = std::shared_ptr<OculusPlatformPlugin>;
|
||||
using InputPluginSettingsPersister = std::function<void(const InputPluginList&)>;
|
||||
|
|
14
libraries/plugins/src/plugins/OculusPlatformPlugin.cpp
Normal file
14
libraries/plugins/src/plugins/OculusPlatformPlugin.cpp
Normal file
|
@ -0,0 +1,14 @@
|
|||
//
|
||||
// Created by Wayne Chen on 2018/12/20
|
||||
// Copyright 2018 High Fidelity Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2-0.html
|
||||
//
|
||||
#include "OculusPlatformPlugin.h"
|
||||
|
||||
OculusPlatformPlugin::OculusPlatformPlugin() {
|
||||
}
|
||||
|
||||
OculusPlatformPlugin::~OculusPlatformPlugin() {
|
||||
}
|
|
@ -7,30 +7,21 @@
|
|||
//
|
||||
#pragma once
|
||||
|
||||
#include <QtCore/QByteArray>
|
||||
#include <QObject>
|
||||
#include <QtCore/QString>
|
||||
|
||||
#include <functional>
|
||||
|
||||
using OculusTicketRequestCallback = std::function<void(QString, QString)>;
|
||||
|
||||
|
||||
class OculusPlatformPlugin {
|
||||
class OculusPlatformPlugin : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
virtual ~OculusPlatformPlugin() = default;
|
||||
OculusPlatformPlugin();
|
||||
virtual ~OculusPlatformPlugin();
|
||||
|
||||
virtual bool init() = 0;
|
||||
virtual void shutdown() = 0;
|
||||
virtual const QString getName() const = 0;
|
||||
|
||||
virtual bool isRunning() = 0;
|
||||
virtual void handleOVREvents() = 0;
|
||||
|
||||
virtual void runCallbacks() = 0;
|
||||
|
||||
virtual void requestTicket(OculusTicketRequestCallback callback) = 0;
|
||||
|
||||
virtual QString getUserProof() = 0;
|
||||
|
||||
virtual QString getLoggedInUserID() = 0;
|
||||
|
||||
virtual QString getOculusVRBuildID() = 0;
|
||||
signals:
|
||||
void nonceAndUserIDChanged(QString nonce, QString userID);
|
||||
};
|
||||
|
|
|
@ -179,19 +179,20 @@ const SteamClientPluginPointer PluginManager::getSteamClientPlugin() {
|
|||
return steamClientPlugin;
|
||||
}
|
||||
|
||||
const OculusDisplayPluginPointer PluginManager::getOculusDisplayPlugin() {
|
||||
static OculusDisplayPluginPointer oculusDisplayPlugin;
|
||||
const OculusPlatformPluginPointer PluginManager::getOculusPlatformPlugin() {
|
||||
static OculusPlatformPluginPointer oculusPlatformPlugin;
|
||||
static std::once_flag once;
|
||||
std::call_once(once, [&] {
|
||||
// Now grab the display plugins - might break in the main update loop if user unplugs the headset I think?
|
||||
for (auto plugin : getDisplayPlugins()) {
|
||||
if (plugin->getName() == "Oculus Rift") {
|
||||
oculusDisplayPlugin = plugin;
|
||||
// Now grab the dynamic plugins
|
||||
for (auto loader : getLoadedPlugins()) {
|
||||
OculusPlatformProvider* oculusPlatformProvider = qobject_cast<OculusPlatformProvider*>(loader->instance());
|
||||
if (oculusPlatformProvider) {
|
||||
oculusPlatformPlugin = oculusPlatformProvider->getOculusPlatformPlugin();
|
||||
break;
|
||||
}
|
||||
}
|
||||
});
|
||||
return oculusDisplayPlugin;
|
||||
return oculusPlatformPlugin;
|
||||
}
|
||||
|
||||
const DisplayPluginList& PluginManager::getDisplayPlugins() {
|
||||
|
|
|
@ -28,7 +28,7 @@ public:
|
|||
const InputPluginList& getInputPlugins();
|
||||
const CodecPluginList& getCodecPlugins();
|
||||
const SteamClientPluginPointer getSteamClientPlugin();
|
||||
const OculusDisplayPluginPointer getOculusDisplayPlugin();
|
||||
const OculusPlatformPluginPointer getOculusPlatformPlugin();
|
||||
|
||||
DisplayPluginList getPreferredDisplayPlugins();
|
||||
void setPreferredDisplayPlugins(const QStringList& displays);
|
||||
|
|
|
@ -34,8 +34,6 @@ if (NOT SERVER_ONLY AND NOT ANDROID)
|
|||
add_subdirectory(${DIR})
|
||||
set(DIR "steamClient")
|
||||
add_subdirectory(${DIR})
|
||||
set(DIR "oculusPlatform")
|
||||
add_subdirectory(${DIR})
|
||||
set(DIR "hifiLeapMotion")
|
||||
add_subdirectory(${DIR})
|
||||
endif()
|
||||
|
|
|
@ -227,73 +227,3 @@ QVector<glm::vec3> OculusBaseDisplayPlugin::getSensorPositions() {
|
|||
|
||||
return result;
|
||||
}
|
||||
|
||||
void OculusBaseDisplayPlugin::handleOVREvents() {
|
||||
#ifdef OCULUS_APP_ID
|
||||
if (qApp->property(hifi::properties::OCULUS_STORE).toBool()) {
|
||||
// pop messages to see if we got a return for an entitlement check
|
||||
ovrMessageHandle message = ovr_PopMessage();
|
||||
|
||||
while (message) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_Entitlement_GetIsViewerEntitled: {
|
||||
_isViewerEntitled = !ovr_Message_IsError(message);
|
||||
if (_isViewerEntitled) {
|
||||
// this viewer is entitled, no need to flag anything
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check succeeded, proceeding normally";
|
||||
} else {
|
||||
// we failed the entitlement check, quit
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check failed, app will now quit" << OCULUS_APP_ID;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_Get: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
qCDebug(oculusLog) << "Oculus Platform user retrieval succeeded";
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
_user = ovr_User_GetOculusID(user);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform user retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
_user = "";
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_GetLoggedInUser: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
_userID = ovr_User_GetID(user);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform user ID retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_GetUserProof: {
|
||||
_nonceChanged = true;
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
ovrUserProofHandle userProof = ovr_Message_GetUserProof(message);
|
||||
_nonce = ovr_UserProof_GetNonce(userProof);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform nonce retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
_nonce = "";
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (_nonceChanged) {
|
||||
emit nonceAndUserIDChanged(_nonce, _user);
|
||||
_nonce = _user = "";
|
||||
_nonceChanged = false;
|
||||
}
|
||||
|
||||
// free the message handle to cleanup and not leak
|
||||
ovr_FreeMessage(message);
|
||||
|
||||
// pop the next message to check, if there is one
|
||||
message = ovr_PopMessage();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -43,7 +43,6 @@ protected:
|
|||
bool internalActivate() override;
|
||||
void internalDeactivate() override;
|
||||
void updatePresentPose() override;
|
||||
void handleOVREvents();
|
||||
|
||||
protected:
|
||||
bool _isViewerEntitled;
|
||||
|
|
|
@ -56,10 +56,6 @@ void OculusDisplayPlugin::init() {
|
|||
emit deviceConnected(getName());
|
||||
}
|
||||
|
||||
void OculusDisplayPlugin::pluginUpdate() {
|
||||
handleOVREvents();
|
||||
}
|
||||
|
||||
void OculusDisplayPlugin::cycleDebugOutput() {
|
||||
if (_session) {
|
||||
currentDebugMode = static_cast<ovrPerfHudMode>((currentDebugMode + 1) % ovrPerfHud_Count);
|
||||
|
|
|
@ -23,7 +23,6 @@ public:
|
|||
float getTargetFrameRate() const override;
|
||||
|
||||
virtual QJsonObject getHardwareStats() const;
|
||||
void pluginUpdate() override final;
|
||||
|
||||
protected:
|
||||
QThread::Priority getPresentPriority() override { return QThread::TimeCriticalPriority; }
|
||||
|
|
95
plugins/oculus/src/OculusPlatformPlugin.cpp
Normal file
95
plugins/oculus/src/OculusPlatformPlugin.cpp
Normal file
|
@ -0,0 +1,95 @@
|
|||
//
|
||||
// Created by Wayne Chen on 2019/01/08
|
||||
// Copyright 2019 High Fidelity, Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
|
||||
#include "OculusPlatformPlugin.h"
|
||||
|
||||
#include <shared/GlobalAppProperties.h>
|
||||
|
||||
#include <QMetaObject>
|
||||
|
||||
#include "OculusHelpers.h"
|
||||
|
||||
const char* OculusAPIPlugin::NAME { "Oculus Rift" };
|
||||
|
||||
OculusAPIPlugin::OculusAPIPlugin() {
|
||||
_session = hifi::ovr::acquireRenderSession();
|
||||
}
|
||||
|
||||
OculusAPIPlugin::~OculusAPIPlugin() {
|
||||
hifi::ovr::releaseRenderSession(_session);
|
||||
}
|
||||
|
||||
void OculusAPIPlugin::handleOVREvents() {
|
||||
#ifdef OCULUS_APP_ID
|
||||
if (qApp->property(hifi::properties::OCULUS_STORE).toBool()) {
|
||||
// pop messages to see if we got a return for an entitlement check
|
||||
ovrMessageHandle message = ovr_PopMessage();
|
||||
|
||||
while (message) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_Entitlement_GetIsViewerEntitled: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
// this viewer is entitled, no need to flag anything
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check succeeded, proceeding normally";
|
||||
} else {
|
||||
// we failed the entitlement check, quit
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check failed, app will now quit" << OCULUS_APP_ID;
|
||||
QMetaObject::invokeMethod(qApp, "quit");
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_Get: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
qCDebug(oculusLog) << "Oculus Platform user retrieval succeeded";
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
_user = ovr_User_GetOculusID(user);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform user retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
_user = "";
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_GetLoggedInUser: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
_userID = ovr_User_GetID(user);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform user ID retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
}
|
||||
break;
|
||||
}
|
||||
case ovrMessage_User_GetUserProof: {
|
||||
_nonceChanged = true;
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
ovrUserProofHandle userProof = ovr_Message_GetUserProof(message);
|
||||
_nonce = ovr_UserProof_GetNonce(userProof);
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Oculus Platform nonce retrieval failed" << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
_nonce = "";
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (_nonceChanged) {
|
||||
emit nonceAndUserIDChanged(_nonce, _user);
|
||||
_nonce = _user = "";
|
||||
_nonceChanged = false;
|
||||
}
|
||||
|
||||
// free the message handle to cleanup and not leak
|
||||
ovr_FreeMessage(message);
|
||||
|
||||
// pop the next message to check, if there is one
|
||||
message = ovr_PopMessage();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
32
plugins/oculus/src/OculusPlatformPlugin.h
Normal file
32
plugins/oculus/src/OculusPlatformPlugin.h
Normal file
|
@ -0,0 +1,32 @@
|
|||
//
|
||||
// Created by Wayne Chen on 2019/01/08
|
||||
// Copyright 2019 High Fidelity, Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
#pragma once
|
||||
|
||||
#include <plugins/OculusPlatformPlugin.h>
|
||||
|
||||
#include <OVR_CAPI_GL.h>
|
||||
|
||||
#define OVRPL_DISABLED
|
||||
#include <OVR_Platform.h>
|
||||
|
||||
class OculusAPIPlugin : public OculusPlatformPlugin {
|
||||
public:
|
||||
OculusAPIPlugin();
|
||||
virtual ~OculusAPIPlugin();
|
||||
const QString getName() const { return NAME; }
|
||||
|
||||
virtual void handleOVREvents();
|
||||
|
||||
private:
|
||||
static const char* NAME;
|
||||
QString _nonce;
|
||||
bool _nonceChanged;
|
||||
QString _user;
|
||||
ovrID _userID;
|
||||
ovrSession _session{ nullptr };
|
||||
};
|
|
@ -18,15 +18,18 @@
|
|||
|
||||
#include "OculusDisplayPlugin.h"
|
||||
#include "OculusDebugDisplayPlugin.h"
|
||||
#include "OculusPlatformPlugin.h"
|
||||
#include "OculusControllerManager.h"
|
||||
|
||||
class OculusProvider : public QObject, public DisplayProvider, InputProvider
|
||||
class OculusProvider : public QObject, public DisplayProvider, InputProvider, OculusPlatformProvider
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PLUGIN_METADATA(IID DisplayProvider_iid FILE "oculus.json")
|
||||
Q_INTERFACES(DisplayProvider)
|
||||
Q_PLUGIN_METADATA(IID InputProvider_iid FILE "oculus.json")
|
||||
Q_INTERFACES(InputProvider)
|
||||
Q_PLUGIN_METADATA(IID OculusPlatformProvider_iid FILE "oculus.json")
|
||||
Q_INTERFACES(OculusPlatformProvider)
|
||||
|
||||
public:
|
||||
OculusProvider(QObject* parent = nullptr) : QObject(parent) {}
|
||||
|
@ -62,6 +65,15 @@ public:
|
|||
return _inputPlugins;
|
||||
}
|
||||
|
||||
virtual OculusPlatformPluginPointer getOculusPlatformPlugin() override {
|
||||
static std::once_flag once;
|
||||
std::call_once(once, [&] {
|
||||
_oculusPlatformPlugin = std::make_shared<OculusAPIPlugin>();
|
||||
|
||||
});
|
||||
return _oculusPlatformPlugin;
|
||||
}
|
||||
|
||||
virtual void destroyInputPlugins() override {
|
||||
_inputPlugins.clear();
|
||||
}
|
||||
|
@ -73,6 +85,7 @@ public:
|
|||
private:
|
||||
DisplayPluginList _displayPlugins;
|
||||
InputPluginList _inputPlugins;
|
||||
OculusPlatformPluginPointer _oculusPlatformPlugin;
|
||||
};
|
||||
|
||||
#include "OculusProvider.moc"
|
||||
|
|
|
@ -1,36 +0,0 @@
|
|||
#
|
||||
# Created by Bradley Austin Davis on 2015/10/25
|
||||
# Copyright 2015 High Fidelity, Inc.
|
||||
#
|
||||
# Distributed under the Apache License, Version 2.0.
|
||||
# See the accompanying file LICENSE or http:#www.apache.org/licenses/LICENSE-2.0.html
|
||||
#
|
||||
|
||||
if (WIN32 AND (NOT USE_GLES))
|
||||
|
||||
# if we were passed an Oculus App ID for entitlement checks, send that along
|
||||
if (DEFINED ENV{OCULUS_APP_ID})
|
||||
add_definitions(-DOCULUS_APP_ID="$ENV{OCULUS_APP_ID}")
|
||||
endif ()
|
||||
|
||||
set(TARGET_NAME oculusPlatform)
|
||||
setup_hifi_plugin(Multimedia)
|
||||
link_hifi_libraries(
|
||||
shared task gl shaders gpu ${PLATFORM_GL_BACKEND} controllers ui qml
|
||||
plugins ui-plugins display-plugins input-plugins
|
||||
audio-client networking render-utils
|
||||
${PLATFORM_GL_BACKEND}
|
||||
)
|
||||
include_hifi_library_headers(octree)
|
||||
|
||||
add_dependency_external_projects(LibOVR)
|
||||
find_package(LibOVR REQUIRED)
|
||||
target_include_directories(${TARGET_NAME} PRIVATE ${LIBOVR_INCLUDE_DIRS})
|
||||
target_link_libraries(${TARGET_NAME} ${LIBOVR_LIBRARIES})
|
||||
target_link_libraries(${TARGET_NAME} Winmm.lib)
|
||||
|
||||
add_dependency_external_projects(LibOVRPlatform)
|
||||
find_package(LibOVRPlatform REQUIRED)
|
||||
target_include_directories(${TARGET_NAME} PRIVATE ${LIBOVRPLATFORM_INCLUDE_DIRS})
|
||||
target_link_libraries(${TARGET_NAME} ${LIBOVRPLATFORM_LIBRARIES})
|
||||
endif()
|
|
@ -1,226 +0,0 @@
|
|||
//
|
||||
// Created by Wayne Chen on 2018/12/20
|
||||
// Copyright 2018 High Fidelity Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2-0.html
|
||||
//
|
||||
|
||||
#include "OculusAPIPlugin.h"
|
||||
|
||||
#include <atomic>
|
||||
#include <chrono>
|
||||
#include <thread>
|
||||
|
||||
#include <QtCore/QTimer>
|
||||
|
||||
#define OVRPL_DISABLED
|
||||
#include <OVR_Platform.h>
|
||||
|
||||
#include <shared/GlobalAppProperties.h>
|
||||
#include "OculusHelpers.h"
|
||||
|
||||
static std::atomic_bool initialized { false };
|
||||
static ovrSession session { nullptr };
|
||||
|
||||
bool OculusAPIPlugin::init() {
|
||||
if (session) {
|
||||
return initialized;
|
||||
}
|
||||
|
||||
ovrInitParams initParams{ ovrInit_RequestVersion | ovrInit_FocusAware, OVR_MINOR_VERSION, nullptr, 0, 0 };
|
||||
initParams.Flags |= ovrInit_Invisible;
|
||||
|
||||
if (!OVR_SUCCESS(ovr_Initialize(&initParams))) {
|
||||
qCWarning(oculusLog) << "Failed to initialze Oculus SDK" << hifi::ovr::getError();
|
||||
return initialized;
|
||||
}
|
||||
|
||||
#ifdef OCULUS_APP_ID
|
||||
if (qApp->property(hifi::properties::OCULUS_STORE).toBool()) {
|
||||
auto result = ovr_PlatformInitializeWindows(OCULUS_APP_ID);
|
||||
if (result != ovrPlatformInitialize_Success && result != ovrPlatformInitialize_PreLoaded) {
|
||||
qCWarning(oculusLog) << "Unable to initialize the platform for entitlement check - fail the check" << hifi::ovr::getError();
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Performing Oculus Platform entitlement check";
|
||||
ovr_Entitlement_GetIsViewerEntitled();
|
||||
QTimer timer;
|
||||
timer.start(1000);
|
||||
using namespace std::chrono_literals;
|
||||
std::this_thread::sleep_for(50ms);
|
||||
while (auto message = ovr_PopMessage()) {
|
||||
if (timer.remainingTime() == 0) {
|
||||
qCDebug(oculusLog) << "login user id timeout after 1 second";
|
||||
break;
|
||||
}
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_Entitlement_GetIsViewerEntitled:
|
||||
if (ovr_Message_IsError(message)) {
|
||||
qDebug() << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
}
|
||||
initialized = true;
|
||||
default:
|
||||
ovr_FreeMessage(message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return initialized;
|
||||
}
|
||||
|
||||
void OculusAPIPlugin::shutdown() {
|
||||
}
|
||||
|
||||
void OculusAPIPlugin::runCallbacks() {
|
||||
}
|
||||
|
||||
void OculusAPIPlugin::requestTicket(OculusTicketRequestCallback callback) {
|
||||
if (!initialized) {
|
||||
if (!ovr_IsPlatformInitialized()) {
|
||||
init();
|
||||
}
|
||||
else {
|
||||
qWarning() << "Oculus is not running";
|
||||
callback("", "");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (!initialized) {
|
||||
qDebug() << "Oculus not initialized";
|
||||
return;
|
||||
}
|
||||
|
||||
auto nonce = getUserProof();
|
||||
auto userID = getLoggedInUserID();
|
||||
qDebug() << "Nonce: " << nonce << ", " << userID;
|
||||
|
||||
callback(nonce, userID);
|
||||
return;
|
||||
}
|
||||
|
||||
bool OculusAPIPlugin::isRunning() {
|
||||
return initialized;
|
||||
}
|
||||
|
||||
QString OculusAPIPlugin::getUserProof() {
|
||||
if (initialized) {
|
||||
QTimer timer;
|
||||
timer.start(5000);
|
||||
auto request = ovr_User_GetUserProof();
|
||||
ovrMessageHandle message { nullptr };
|
||||
bool messageNotReceived = true;
|
||||
while (messageNotReceived) {
|
||||
message = ovr_PopMessage();
|
||||
if (timer.remainingTime() == 0) {
|
||||
qCDebug(oculusLog) << "user proof timeout after 5 seconds";
|
||||
return "";
|
||||
}
|
||||
if (message != nullptr) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_User_GetUserProof:
|
||||
messageNotReceived = false;
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
ovrUserProofHandle userProof = ovr_Message_GetUserProof(message);
|
||||
QString nonce = ovr_UserProof_GetNonce(userProof);
|
||||
ovr_FreeMessage(message);
|
||||
return nonce;
|
||||
} else {
|
||||
qDebug() << "Error getting user proof: " << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
ovr_FreeMessage(message);
|
||||
return "";
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ovr_FreeMessage(message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
QString getOculusUserID(ovrID userID) {
|
||||
QTimer timer;
|
||||
timer.start(5000);
|
||||
timer.setSingleShot(true);
|
||||
auto request = ovr_User_Get(userID);
|
||||
bool messageNotReceived = true;
|
||||
while (messageNotReceived) {
|
||||
auto message = ovr_PopMessage();
|
||||
if (timer.remainingTime() == 0) {
|
||||
qCDebug(oculusLog) << "login user id timeout after 5 seconds";
|
||||
return "";
|
||||
}
|
||||
if (message != nullptr) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_User_Get:
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
messageNotReceived = false;
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
qCDebug(oculusLog) << "UserID: " << userID << "\nOculus ID: " << QString(ovr_User_GetOculusID(user));
|
||||
return QString(ovr_User_GetOculusID(user));
|
||||
} else {
|
||||
qDebug() << "Error getting user id: " << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
ovr_FreeMessage(message);
|
||||
return "";
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ovr_FreeMessage(message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
QString OculusAPIPlugin::getLoggedInUserID() {
|
||||
if (initialized) {
|
||||
QTimer timer;
|
||||
timer.start(5000);
|
||||
timer.setSingleShot(true);
|
||||
auto request = ovr_User_GetLoggedInUser();
|
||||
ovrMessageHandle message { nullptr };
|
||||
ovrID userID = 0;
|
||||
bool messageNotReceived = true;
|
||||
while (messageNotReceived) {
|
||||
message = ovr_PopMessage();
|
||||
if (timer.remainingTime() == 0) {
|
||||
qCDebug(oculusLog) << "login user id timeout after 5 seconds";
|
||||
return "";
|
||||
}
|
||||
if (message != nullptr) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_User_GetLoggedInUser:
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
messageNotReceived = false;
|
||||
ovrUserHandle user = ovr_Message_GetUser(message);
|
||||
ovr_FreeMessage(message);
|
||||
userID = ovr_User_GetID(user);
|
||||
break;
|
||||
} else {
|
||||
qDebug() << "Error getting user id: " << QString(ovr_Error_GetMessage(ovr_Message_GetError(message)));
|
||||
ovr_FreeMessage(message);
|
||||
return "";
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ovr_FreeMessage(message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
timer.stop();
|
||||
return getOculusUserID(userID);
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
QString OculusAPIPlugin::getOculusVRBuildID() {
|
||||
return QString(OVR_MAJOR_VERSION + "." + OVR_MINOR_VERSION);
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
//
|
||||
// Created by Wayne Chen on 2018/12/20
|
||||
// Copyright 2018 High Fidelity Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2-0.html
|
||||
//
|
||||
#pragma once
|
||||
|
||||
#include <plugins/OculusPlatformPlugin.h>
|
||||
|
||||
class OculusAPIPlugin : public OculusPlatformPlugin {
|
||||
public:
|
||||
bool init() override;
|
||||
void shutdown() override;
|
||||
|
||||
bool isRunning() override;
|
||||
|
||||
void runCallbacks() override;
|
||||
|
||||
void requestTicket(OculusTicketRequestCallback callback) override;
|
||||
|
||||
QString getUserProof() override;
|
||||
QString getLoggedInUserID() override;
|
||||
|
||||
QString getOculusVRBuildID() override;
|
||||
};
|
|
@ -1,326 +0,0 @@
|
|||
//
|
||||
// Created by Bradley Austin Davis on 2015/08/08
|
||||
// Copyright 2015 High Fidelity, Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
|
||||
#include "OculusHelpers.h"
|
||||
|
||||
#include <atomic>
|
||||
|
||||
#include <Windows.h>
|
||||
#include <QtCore/QFile>
|
||||
#include <QtCore/QDir>
|
||||
#include <QtCore/QProcessEnvironment>
|
||||
|
||||
#define OVRPL_DISABLED
|
||||
#include <OVR_Platform.h>
|
||||
|
||||
#include <controllers/Input.h>
|
||||
#include <controllers/Pose.h>
|
||||
#include <shared/GlobalAppProperties.h>
|
||||
#include <NumericalConstants.h>
|
||||
|
||||
Q_LOGGING_CATEGORY(displayplugins, "hifi.plugins.display")
|
||||
Q_LOGGING_CATEGORY(oculusLog, "hifi.plugins.display.oculus")
|
||||
|
||||
using namespace hifi;
|
||||
|
||||
static wchar_t* REQUIRED_OCULUS_DLL = L"LibOVRRT64_1.dll";
|
||||
static wchar_t FOUND_PATH[MAX_PATH];
|
||||
|
||||
bool ovr::available() {
|
||||
static std::once_flag once;
|
||||
static bool result{ false };
|
||||
std::call_once(once, [&] {
|
||||
static const QString DEBUG_FLAG("HIFI_DEBUG_OPENVR");
|
||||
static bool enableDebugOpenVR = QProcessEnvironment::systemEnvironment().contains(DEBUG_FLAG);
|
||||
if (enableDebugOpenVR) {
|
||||
return;
|
||||
}
|
||||
|
||||
ovrDetectResult detect = ovr_Detect(0);
|
||||
if (!detect.IsOculusServiceRunning || !detect.IsOculusHMDConnected) {
|
||||
return;
|
||||
}
|
||||
|
||||
DWORD searchResult = SearchPathW(NULL, REQUIRED_OCULUS_DLL, NULL, MAX_PATH, FOUND_PATH, NULL);
|
||||
if (searchResult <= 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
result = true;
|
||||
});
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
class ovrImpl {
|
||||
using Mutex = std::mutex;
|
||||
using Lock = std::unique_lock<Mutex>;
|
||||
std::mutex mutex;
|
||||
ovrSession session{ nullptr };
|
||||
size_t renderCount{ 0 };
|
||||
|
||||
private:
|
||||
void setupSession(bool render) {
|
||||
if (session) {
|
||||
return;
|
||||
}
|
||||
ovrInitParams initParams{ ovrInit_RequestVersion | ovrInit_FocusAware, OVR_MINOR_VERSION, nullptr, 0, 0 };
|
||||
if (render) {
|
||||
initParams.Flags |= ovrInit_MixedRendering;
|
||||
} else {
|
||||
initParams.Flags |= ovrInit_Invisible;
|
||||
}
|
||||
|
||||
if (!OVR_SUCCESS(ovr_Initialize(&initParams))) {
|
||||
qCWarning(oculusLog) << "Failed to initialze Oculus SDK" << ovr::getError();
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef OCULUS_APP_ID
|
||||
if (qApp->property(hifi::properties::OCULUS_STORE).toBool()) {
|
||||
if (ovr_PlatformInitializeWindows(OCULUS_APP_ID) != ovrPlatformInitialize_Success) {
|
||||
qCWarning(oculusLog) << "Unable to initialize the platform for entitlement check - fail the check" << ovr::getError();
|
||||
return;
|
||||
} else {
|
||||
qCDebug(oculusLog) << "Performing Oculus Platform entitlement check";
|
||||
ovr_Entitlement_GetIsViewerEntitled();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
ovrGraphicsLuid luid;
|
||||
if (!OVR_SUCCESS(ovr_Create(&session, &luid))) {
|
||||
qCWarning(oculusLog) << "Failed to acquire Oculus session" << ovr::getError();
|
||||
return;
|
||||
} else {
|
||||
ovrResult setFloorLevelOrigin = ovr_SetTrackingOriginType(session, ovrTrackingOrigin::ovrTrackingOrigin_FloorLevel);
|
||||
if (!OVR_SUCCESS(setFloorLevelOrigin)) {
|
||||
qCWarning(oculusLog) << "Failed to set the Oculus tracking origin to floor level" << ovr::getError();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void releaseSession() {
|
||||
if (!session) {
|
||||
return;
|
||||
}
|
||||
ovr_Destroy(session);
|
||||
session = nullptr;
|
||||
ovr_Shutdown();
|
||||
}
|
||||
|
||||
public:
|
||||
void withSession(const std::function<void(ovrSession)>& f) {
|
||||
Lock lock(mutex);
|
||||
if (!session) {
|
||||
setupSession(false);
|
||||
}
|
||||
f(session);
|
||||
}
|
||||
|
||||
ovrSession acquireRenderSession() {
|
||||
Lock lock(mutex);
|
||||
if (renderCount++ == 0) {
|
||||
releaseSession();
|
||||
setupSession(true);
|
||||
}
|
||||
return session;
|
||||
}
|
||||
|
||||
void releaseRenderSession(ovrSession session) {
|
||||
Lock lock(mutex);
|
||||
if (--renderCount == 0) {
|
||||
releaseSession();
|
||||
}
|
||||
}
|
||||
} _ovr;
|
||||
|
||||
ovrSession ovr::acquireRenderSession() {
|
||||
return _ovr.acquireRenderSession();
|
||||
}
|
||||
|
||||
void ovr::releaseRenderSession(ovrSession session) {
|
||||
_ovr.releaseRenderSession(session);
|
||||
}
|
||||
|
||||
void ovr::withSession(const std::function<void(ovrSession)>& f) {
|
||||
_ovr.withSession(f);
|
||||
}
|
||||
|
||||
ovrSessionStatus ovr::getStatus() {
|
||||
ovrResult result;
|
||||
return ovr::getStatus(result);
|
||||
}
|
||||
|
||||
ovrSessionStatus ovr::getStatus(ovrResult& result) {
|
||||
ovrSessionStatus status{};
|
||||
withSession([&](ovrSession session) {
|
||||
result = ovr_GetSessionStatus(session, &status);
|
||||
if (!OVR_SUCCESS(result)) {
|
||||
qCWarning(oculusLog) << "Failed to get session status" << ovr::getError();
|
||||
}
|
||||
});
|
||||
return status;
|
||||
}
|
||||
|
||||
ovrTrackingState ovr::getTrackingState(double absTime, ovrBool latencyMarker) {
|
||||
ovrTrackingState result{};
|
||||
withSession([&](ovrSession session) { result = ovr_GetTrackingState(session, absTime, latencyMarker); });
|
||||
return result;
|
||||
}
|
||||
|
||||
QString ovr::getError() {
|
||||
static ovrErrorInfo error;
|
||||
ovr_GetLastErrorInfo(&error);
|
||||
return QString(error.ErrorString);
|
||||
}
|
||||
|
||||
controller::Pose hifi::ovr::toControllerPose(ovrHandType hand, const ovrPoseStatef& handPose) {
|
||||
// When the sensor-to-world rotation is identity the coordinate axes look like this:
|
||||
//
|
||||
// user
|
||||
// forward
|
||||
// -z
|
||||
// |
|
||||
// y| user
|
||||
// y o----x right
|
||||
// o-----x user
|
||||
// | up
|
||||
// |
|
||||
// z
|
||||
//
|
||||
// Rift
|
||||
|
||||
// From ABOVE the hand canonical axes looks like this:
|
||||
//
|
||||
// | | | | y | | | |
|
||||
// | | | | | | | | |
|
||||
// | | | | |
|
||||
// |left | / x---- + \ |right|
|
||||
// | _/ z \_ |
|
||||
// | | | |
|
||||
// | | | |
|
||||
//
|
||||
|
||||
// So when the user is in Rift space facing the -zAxis with hands outstretched and palms down
|
||||
// the rotation to align the Touch axes with those of the hands is:
|
||||
//
|
||||
// touchToHand = halfTurnAboutY * quaterTurnAboutX
|
||||
|
||||
// Due to how the Touch controllers fit into the palm there is an offset that is different for each hand.
|
||||
// You can think of this offset as the inverse of the measured rotation when the hands are posed, such that
|
||||
// the combination (measurement * offset) is identity at this orientation.
|
||||
//
|
||||
// Qoffset = glm::inverse(deltaRotation when hand is posed fingers forward, palm down)
|
||||
//
|
||||
// An approximate offset for the Touch can be obtained by inspection:
|
||||
//
|
||||
// Qoffset = glm::inverse(glm::angleAxis(sign * PI/2.0f, zAxis) * glm::angleAxis(PI/4.0f, xAxis))
|
||||
//
|
||||
// So the full equation is:
|
||||
//
|
||||
// Q = combinedMeasurement * touchToHand
|
||||
//
|
||||
// Q = (deltaQ * QOffset) * (yFlip * quarterTurnAboutX)
|
||||
//
|
||||
// Q = (deltaQ * inverse(deltaQForAlignedHand)) * (yFlip * quarterTurnAboutX)
|
||||
static const glm::quat yFlip = glm::angleAxis(PI, Vectors::UNIT_Y);
|
||||
static const glm::quat quarterX = glm::angleAxis(PI_OVER_TWO, Vectors::UNIT_X);
|
||||
static const glm::quat touchToHand = yFlip * quarterX;
|
||||
|
||||
static const glm::quat leftQuarterZ = glm::angleAxis(-PI_OVER_TWO, Vectors::UNIT_Z);
|
||||
static const glm::quat rightQuarterZ = glm::angleAxis(PI_OVER_TWO, Vectors::UNIT_Z);
|
||||
|
||||
static const glm::quat leftRotationOffset = glm::inverse(leftQuarterZ) * touchToHand;
|
||||
static const glm::quat rightRotationOffset = glm::inverse(rightQuarterZ) * touchToHand;
|
||||
|
||||
static const float CONTROLLER_LENGTH_OFFSET = 0.0762f; // three inches
|
||||
static const glm::vec3 CONTROLLER_OFFSET =
|
||||
glm::vec3(CONTROLLER_LENGTH_OFFSET / 2.0f, -CONTROLLER_LENGTH_OFFSET / 2.0f, CONTROLLER_LENGTH_OFFSET * 1.5f);
|
||||
static const glm::vec3 leftTranslationOffset = glm::vec3(-1.0f, 1.0f, 1.0f) * CONTROLLER_OFFSET;
|
||||
static const glm::vec3 rightTranslationOffset = CONTROLLER_OFFSET;
|
||||
|
||||
auto translationOffset = (hand == ovrHand_Left ? leftTranslationOffset : rightTranslationOffset);
|
||||
auto rotationOffset = (hand == ovrHand_Left ? leftRotationOffset : rightRotationOffset);
|
||||
|
||||
glm::quat rotation = toGlm(handPose.ThePose.Orientation);
|
||||
|
||||
controller::Pose pose;
|
||||
pose.translation = toGlm(handPose.ThePose.Position);
|
||||
pose.translation += rotation * translationOffset;
|
||||
pose.rotation = rotation * rotationOffset;
|
||||
pose.angularVelocity = rotation * toGlm(handPose.AngularVelocity);
|
||||
pose.velocity = toGlm(handPose.LinearVelocity);
|
||||
pose.valid = true;
|
||||
return pose;
|
||||
}
|
||||
|
||||
controller::Pose hifi::ovr::toControllerPose(ovrHandType hand,
|
||||
const ovrPoseStatef& handPose,
|
||||
const ovrPoseStatef& lastHandPose) {
|
||||
static const glm::quat yFlip = glm::angleAxis(PI, Vectors::UNIT_Y);
|
||||
static const glm::quat quarterX = glm::angleAxis(PI_OVER_TWO, Vectors::UNIT_X);
|
||||
static const glm::quat touchToHand = yFlip * quarterX;
|
||||
|
||||
static const glm::quat leftQuarterZ = glm::angleAxis(-PI_OVER_TWO, Vectors::UNIT_Z);
|
||||
static const glm::quat rightQuarterZ = glm::angleAxis(PI_OVER_TWO, Vectors::UNIT_Z);
|
||||
|
||||
static const glm::quat leftRotationOffset = glm::inverse(leftQuarterZ) * touchToHand;
|
||||
static const glm::quat rightRotationOffset = glm::inverse(rightQuarterZ) * touchToHand;
|
||||
|
||||
static const float CONTROLLER_LENGTH_OFFSET = 0.0762f; // three inches
|
||||
static const glm::vec3 CONTROLLER_OFFSET =
|
||||
glm::vec3(CONTROLLER_LENGTH_OFFSET / 2.0f, -CONTROLLER_LENGTH_OFFSET / 2.0f, CONTROLLER_LENGTH_OFFSET * 1.5f);
|
||||
static const glm::vec3 leftTranslationOffset = glm::vec3(-1.0f, 1.0f, 1.0f) * CONTROLLER_OFFSET;
|
||||
static const glm::vec3 rightTranslationOffset = CONTROLLER_OFFSET;
|
||||
|
||||
auto translationOffset = (hand == ovrHand_Left ? leftTranslationOffset : rightTranslationOffset);
|
||||
auto rotationOffset = (hand == ovrHand_Left ? leftRotationOffset : rightRotationOffset);
|
||||
|
||||
glm::quat rotation = toGlm(handPose.ThePose.Orientation);
|
||||
|
||||
controller::Pose pose;
|
||||
pose.translation = toGlm(lastHandPose.ThePose.Position);
|
||||
pose.translation += rotation * translationOffset;
|
||||
pose.rotation = rotation * rotationOffset;
|
||||
pose.angularVelocity = toGlm(lastHandPose.AngularVelocity);
|
||||
pose.velocity = toGlm(lastHandPose.LinearVelocity);
|
||||
pose.valid = true;
|
||||
return pose;
|
||||
}
|
||||
|
||||
bool hifi::ovr::handleOVREvents() {
|
||||
#ifdef OCULUS_APP_ID
|
||||
if (qApp->property(hifi::properties::OCULUS_STORE).toBool()) {
|
||||
// pop messages to see if we got a return for an entitlement check
|
||||
ovrMessageHandle message = ovr_PopMessage();
|
||||
|
||||
while (message) {
|
||||
switch (ovr_Message_GetType(message)) {
|
||||
case ovrMessage_Entitlement_GetIsViewerEntitled: {
|
||||
if (!ovr_Message_IsError(message)) {
|
||||
// this viewer is entitled, no need to flag anything
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check succeeded, proceeding normally";
|
||||
} else {
|
||||
// we failed the entitlement check, quit
|
||||
qCDebug(oculusLog) << "Oculus Platform entitlement check failed, app will now quit" << OCULUS_APP_ID;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// free the message handle to cleanup and not leak
|
||||
ovr_FreeMessage(message);
|
||||
|
||||
// pop the next message to check, if there is one
|
||||
message = ovr_PopMessage();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return true;
|
||||
}
|
|
@ -1,127 +0,0 @@
|
|||
//
|
||||
// Created by Bradley Austin Davis on 2015/05/26
|
||||
// Copyright 2015 High Fidelity, Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
#pragma once
|
||||
|
||||
#include <QtCore/QLoggingCategory>
|
||||
|
||||
#include <ovr_capi.h>
|
||||
#include <GLMHelpers.h>
|
||||
#include <glm/gtc/type_ptr.hpp>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
|
||||
#include <controllers/Forward.h>
|
||||
|
||||
Q_DECLARE_LOGGING_CATEGORY(displayplugins)
|
||||
Q_DECLARE_LOGGING_CATEGORY(oculusLog)
|
||||
|
||||
namespace hifi {
|
||||
|
||||
struct ovr {
|
||||
static bool available();
|
||||
static ovrSession acquireRenderSession();
|
||||
static void releaseRenderSession(ovrSession session);
|
||||
static void withSession(const std::function<void(ovrSession)>& f);
|
||||
static ovrSessionStatus getStatus();
|
||||
static ovrSessionStatus getStatus(ovrResult& result);
|
||||
static ovrTrackingState getTrackingState(double absTime = 0.0, ovrBool latencyMarker = ovrFalse);
|
||||
static QString getError();
|
||||
static bool handleOVREvents();
|
||||
|
||||
static inline bool quitRequested() { return quitRequested(getStatus()); }
|
||||
static inline bool reorientRequested() { return reorientRequested(getStatus()); }
|
||||
static inline bool hmdMounted() { return hmdMounted(getStatus()); }
|
||||
static inline bool hasInputFocus() { return hasInputFocus(getStatus()); }
|
||||
|
||||
static inline bool quitRequested(const ovrSessionStatus& status) { return status.ShouldQuit != ovrFalse; }
|
||||
static inline bool displayLost(const ovrSessionStatus& status) { return status.DisplayLost != ovrFalse; }
|
||||
static inline bool isVisible(const ovrSessionStatus& status) { return status.IsVisible != ovrFalse; }
|
||||
static inline bool reorientRequested(const ovrSessionStatus& status) { return status.ShouldRecenter != ovrFalse; }
|
||||
static inline bool hmdMounted(const ovrSessionStatus& status) { return status.HmdMounted != ovrFalse; }
|
||||
static inline bool hasInputFocus(const ovrSessionStatus& status) { return status.HasInputFocus != ovrFalse; }
|
||||
|
||||
// Convenience method for looping over each eye with a lambda
|
||||
static inline void for_each_eye(const std::function<void(ovrEyeType eye)>& f) {
|
||||
for (ovrEyeType eye = ovrEye_Left; eye < ovrEye_Count; eye = static_cast<ovrEyeType>(eye + 1)) {
|
||||
f(eye);
|
||||
}
|
||||
}
|
||||
|
||||
static inline void for_each_hand(const std::function<void(ovrHandType eye)>& f) {
|
||||
for (ovrHandType hand = ovrHand_Left; hand < ovrHand_Count; hand = static_cast<ovrHandType>(hand + 1)) {
|
||||
f(hand);
|
||||
}
|
||||
}
|
||||
|
||||
static inline glm::mat4 toGlm(const ovrMatrix4f& om) {
|
||||
return glm::transpose(glm::make_mat4(&om.M[0][0]));
|
||||
}
|
||||
|
||||
static inline glm::mat4 toGlm(const ovrFovPort& fovport, float nearPlane = 0.01f, float farPlane = 10000.0f) {
|
||||
return toGlm(ovrMatrix4f_Projection(fovport, nearPlane, farPlane, true));
|
||||
}
|
||||
|
||||
static inline glm::vec3 toGlm(const ovrVector3f& ov) {
|
||||
return glm::make_vec3(&ov.x);
|
||||
}
|
||||
|
||||
static inline glm::vec2 toGlm(const ovrVector2f& ov) {
|
||||
return glm::make_vec2(&ov.x);
|
||||
}
|
||||
|
||||
static inline glm::uvec2 toGlm(const ovrSizei& ov) {
|
||||
return glm::uvec2(ov.w, ov.h);
|
||||
}
|
||||
|
||||
static inline glm::quat toGlm(const ovrQuatf& oq) {
|
||||
return glm::make_quat(&oq.x);
|
||||
}
|
||||
|
||||
static inline glm::mat4 toGlm(const ovrPosef& op) {
|
||||
glm::mat4 orientation = glm::mat4_cast(toGlm(op.Orientation));
|
||||
glm::mat4 translation = glm::translate(glm::mat4(), toGlm(op.Position));
|
||||
return translation * orientation;
|
||||
}
|
||||
|
||||
static inline ovrMatrix4f fromGlm(const glm::mat4& m) {
|
||||
ovrMatrix4f result;
|
||||
glm::mat4 transposed(glm::transpose(m));
|
||||
memcpy(result.M, &(transposed[0][0]), sizeof(float) * 16);
|
||||
return result;
|
||||
}
|
||||
|
||||
static inline ovrVector3f fromGlm(const glm::vec3& v) {
|
||||
return { v.x, v.y, v.z };
|
||||
}
|
||||
|
||||
static inline ovrVector2f fromGlm(const glm::vec2& v) {
|
||||
return { v.x, v.y };
|
||||
}
|
||||
|
||||
static inline ovrSizei fromGlm(const glm::uvec2& v) {
|
||||
return { (int)v.x, (int)v.y };
|
||||
}
|
||||
|
||||
static inline ovrQuatf fromGlm(const glm::quat& q) {
|
||||
return { q.x, q.y, q.z, q.w };
|
||||
}
|
||||
|
||||
static inline ovrPosef poseFromGlm(const glm::mat4& m) {
|
||||
glm::vec3 translation = glm::vec3(m[3]) / m[3].w;
|
||||
glm::quat orientation = glm::quat_cast(m);
|
||||
ovrPosef result;
|
||||
result.Orientation = fromGlm(orientation);
|
||||
result.Position = fromGlm(translation);
|
||||
return result;
|
||||
}
|
||||
|
||||
static controller::Pose toControllerPose(ovrHandType hand, const ovrPoseStatef& handPose);
|
||||
static controller::Pose toControllerPose(ovrHandType hand, const ovrPoseStatef& handPose, const ovrPoseStatef& lastHandPose);
|
||||
|
||||
};
|
||||
|
||||
} // namespace hifi
|
|
@ -1,40 +0,0 @@
|
|||
//
|
||||
// Created by Clément Brisset on 12/14/16
|
||||
// Copyright 2016 High Fidelity, Inc.
|
||||
//
|
||||
// Distributed under the Apache License, Version 2.0.
|
||||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
|
||||
#include <mutex>
|
||||
|
||||
#include <QtCore/QObject>
|
||||
#include <QtCore/QtPlugin>
|
||||
#include <QtCore/QStringList>
|
||||
|
||||
#include <plugins/RuntimePlugin.h>
|
||||
|
||||
#include "OculusAPIPlugin.h"
|
||||
|
||||
class OculusAPIProvider : public QObject, public OculusPlatformProvider {
|
||||
Q_OBJECT
|
||||
Q_PLUGIN_METADATA(IID OculusPlatformProvider_iid FILE "plugin.json")
|
||||
Q_INTERFACES(OculusPlatformProvider)
|
||||
|
||||
public:
|
||||
OculusAPIProvider(QObject* parent = nullptr) : QObject(parent) {}
|
||||
virtual ~OculusAPIProvider() {}
|
||||
|
||||
virtual OculusPlatformPluginPointer getOculusPlatformPlugin() override {
|
||||
static std::once_flag once;
|
||||
std::call_once(once, [&] {
|
||||
_oculusPlatformPlugin = std::make_shared<OculusAPIPlugin>();
|
||||
});
|
||||
return _oculusPlatformPlugin;
|
||||
}
|
||||
|
||||
private:
|
||||
OculusPlatformPluginPointer _oculusPlatformPlugin;
|
||||
};
|
||||
|
||||
#include "OculusPlatformProvider.moc"
|
|
@ -1 +0,0 @@
|
|||
{"name":"Oculus Platform"}
|
Loading…
Reference in a new issue