//// Application.h// interface/src//// Created by Andrzej Kapolka on 5/10/13.// Copyright 2013 High Fidelity, Inc.// Copyright 2020 Vircadia contributors.// Copyright 2022-2023 Overte e.V.//// Distributed under the Apache License, Version 2.0.// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html// SPDX-License-Identifier: Apache-2.0// #ifndef hifi_Application_h#define hifi_Application_h #include <QtWidgets/QApplication> #include <AbstractScriptingServicesInterface.h>#include <AbstractUriHandler.h>#include <AbstractViewStateInterface.h>#include <AvatarHashMap.h>#include <EntityEditPacketSender.h>#include <ModerationFlags.h>#include <OctreeQuery.h>#include <PhysicsEngine.h>#include <ShapeManager.h>#include <TouchEvent.h>#include <ui-plugins/PluginContainer.h> #include "avatar/MyAvatar.h"#include "ConnectionMonitor.h"#include "CursorManager.h"#include "FancyCamera.h"#include "graphics/GraphicsEngine.h"#include "LoginStateManager.h"#include "octree/OctreePacketProcessor.h"#include "PerformanceManager.h"#include "RefreshRateManager.h"#include "scripting/DialogsManagerScriptingInterface.h"#include "ui/ApplicationOverlay.h"#include "ui/OverlayConductor.h"#include "ui/overlays/Overlays.h"#include "VisionSqueeze.h"#include "workload/GameWorkload.h"#ifndef USE_GL#include "VKCanvas.h"#endif class ArchiveDownloadInterface;class AudioInjector;class CompositorHelper;class ControllerScriptingInterface;class DiscordPresence;class EntityScriptServerLogDialog;class FileLogger;class GLCanvas;class KeyboardMouseDevice;class LogDialog;class MainWindow;class ModalDialogListener;class OffscreenUi;class TouchscreenDevice;class TouchscreenVirtualPadDevice;class QCommandLineParser;class QGestureEvent;class QQmlContext;class QQuickItem; namespace controller { class StateController;} class Application;#if defined(qApp)#undef qApp#endif#define qApp (static_cast<Application*>(QCoreApplication::instance())) class Application : public QApplication, public AbstractViewStateInterface, public AbstractScriptingServicesInterface, public AbstractUriHandler, public PluginContainer{ Q_OBJECT public: Application( int& argc, char** argv, QElapsedTimer& startup_time ); ~Application(); /** * @brief Initialize everything * * This is a QApplication, and for Qt reasons it's desirable to create this object * as early as possible. Without that some Qt functions don't work, like QCoreApplication::applicationDirPath() * * So we keep the constructor as minimal as possible, and do the rest of the work in * this function. */ void initialize(const QCommandLineParser &parser); MainWindow* getWindow() const { return _window; } virtual QThread* getMainThread() override { return thread(); } bool isAboutToQuit() const { return _aboutToQuit; } bool isServerlessMode() const; bool isInterstitialMode() const { return _interstitialMode; } bool failedToConnectToEntityServer() const { return _failedToConnectToEntityServer; } void setPreviousSessionCrashed(bool value) { _previousSessionCrashed = value; } // Return an HTTP User-Agent string with OS and device information. Q_INVOKABLE QString getUserAgent(); PerformanceManager& getPerformanceManager() { return _performanceManager; } RefreshRateManager& getRefreshRateManager() { return _refreshRateManager; } float getGameLoopRate() const { return _gameLoopCounter.rate(); } #ifndef Q_OS_ANDROID FileLogger* getLogger() const { return _logger; }#endif bool getUseDiscordPresence() const { return _useDiscordPresence.get(); } void setUseDiscordPresence(bool enable); QString getPreviousScriptLocation() { return _previousScriptLocation.get(); } void setPreviousScriptLocation(const QString& previousScriptLocation) { _previousScriptLocation.set(previousScriptLocation); } void replaceDomainContent(const QString& url, const QString& itemName); void openDirectory(const QString& path); void overrideEntry() { _overrideEntry = true; } void forceDisplayName(const QString& displayName) { getMyAvatar()->setDisplayName(displayName); } void forceLoginWithTokens(const QString& tokens); void setConfigFileURL(const QString& fileUrl); void loadAvatarScripts(const QVector<QString>& urls); void unloadAvatarScripts(); Q_INVOKABLE void copyToClipboard(const QString& text); Q_INVOKABLE void setMinimumGPUTextureMemStabilityCount(int stabilityCount) { _minimumGPUTextureMemSizeStabilityCount = stabilityCount; } virtual ControllerScriptingInterface* getControllerScriptingInterface() { return _controllerScriptingInterface; } virtual void registerScriptEngineWithApplicationServices(ScriptManagerPointer& scriptManager) override; // used by preferences and HMDScriptingInterface... VisionSqueeze& getVisionSqueeze() { return _visionSqueeze; } // UI virtual ui::Menu* getPrimaryMenu() override; virtual void showDisplayPluginsTools(bool show) override;#ifdef USE_GL virtual GLWidget* getPrimaryWidget() override;#else virtual VKWidget* getPrimaryWidget() override;#endif virtual MainWindow* getPrimaryWindow() override; virtual QOpenGLContext* getPrimaryContext() override; virtual bool isForeground() const override; bool hasFocus() const; void setFocus(); void raise(); void showCursor(const Cursor::Icon& cursor); Overlays& getOverlays() { return _overlays; } ApplicationOverlay& getApplicationOverlay() { return *_applicationOverlay; } const ApplicationOverlay& getApplicationOverlay() const { return *_applicationOverlay; } CompositorHelper& getApplicationCompositor() const; virtual PickRay computePickRay(float x, float y) const override; static void setupQmlSurface(QQmlContext* surfaceContext, bool setAdditionalContextProperties); float getHMDTabletScale() { return _hmdTabletScale.get(); } void setHMDTabletScale(float hmdTabletScale) { _hmdTabletScale.set(hmdTabletScale); } float getDesktopTabletScale() { return _desktopTabletScale.get(); } void setDesktopTabletScale(float desktopTabletScale) { _desktopTabletScale.set(desktopTabletScale); } bool getDesktopTabletBecomesToolbarSetting() { return _desktopTabletBecomesToolbarSetting.get(); } void setDesktopTabletBecomesToolbarSetting(bool value); bool getHmdTabletBecomesToolbarSetting() { return _hmdTabletBecomesToolbarSetting.get(); } void setHmdTabletBecomesToolbarSetting(bool value); bool getLogWindowOnTopSetting() { return _keepLogWindowOnTop.get(); } void setLogWindowOnTopSetting(bool keepOnTop) { _keepLogWindowOnTop.set(keepOnTop); } bool getPreferStylusOverLaser() { return _preferStylusOverLaserSetting.get(); } void setPreferStylusOverLaser(bool value) { _preferStylusOverLaserSetting.set(value); } bool getPreferAvatarFingerOverStylus() { return _preferAvatarFingerOverStylusSetting.get(); } void setPreferAvatarFingerOverStylus(bool value) { _preferAvatarFingerOverStylusSetting.set(value); } void setMouseCaptureVR(bool value); bool getMouseCaptureVR(); bool getMiniTabletEnabled() { return _miniTabletEnabledSetting.get(); } void setMiniTabletEnabled(bool enabled); float getSettingConstrainToolbarPosition() { return _constrainToolbarPosition.get(); } void setSettingConstrainToolbarPosition(bool setting); float getAwayStateWhenFocusLostInVREnabled() { return _awayStateWhenFocusLostInVREnabled.get(); } void setAwayStateWhenFocusLostInVREnabled(bool setting); QUuid getTabletScreenID() const; QUuid getTabletHomeButtonID() const; QUuid getTabletFrameID() const; QVector<QUuid> getTabletIDs() const; void confirmConnectWithoutAvatarEntities(); bool getLoginDialogPoppedUp() const { return _loginDialogPoppedUp; } void createLoginDialog(); void updateLoginDialogPosition(); void createAvatarInputsBar(); void destroyAvatarInputsBar(); // Plugins /** * @brief Initialize the plugin manager * * This both does the initial startup and parses arguments. This * is necessary because the plugin manager's options must be set * before any usage of it is made, or they won't apply. * * @param parser */ void initializePluginManager(const QCommandLineParser& parser); virtual void requestReset() override { resetSensors(false); } virtual bool makeRenderingContextCurrent() override { return true; } static void shutdownPlugins(); void initializeDisplayPlugins(); virtual DisplayPluginPointer getActiveDisplayPlugin() const override; void setActiveDisplayPlugin(const QString& pluginName); glm::uvec2 getUiSize() const; QRect getRecommendedHUDRect() const; glm::vec2 getDeviceSize() const; bool isThrottleRendering() const; float getTargetRenderFrameRate() const; // frames/second // Check if a headset is connected bool hasRiftControllers(); bool hasViveControllers(); // the isHMDMode is true whenever we use the interface from an HMD and not a standard flat display // rendering of several elements depend on that // TODO: carry that information on the Camera as a setting virtual bool isHMDMode() const override; glm::mat4 getHMDSensorPose() const; glm::mat4 getEyeOffset(int eye) const; glm::mat4 getEyeProjection(int eye) const; // Graphics void initializeGL(); void initializeRenderEngine(); void initializeUi(); void resizeGL(); glm::uvec2 getCanvasSize() const; float getRenderResolutionScale() const; render::ScenePointer getMain3DScene() override { return _graphicsEngine->getRenderScene(); } render::EnginePointer getRenderEngine() override { return _graphicsEngine->getRenderEngine(); } gpu::ContextPointer getGPUContext() const { return _graphicsEngine->getGPUContext(); } float getRenderLoopRate() const { return _graphicsEngine->getRenderLoopRate(); } // Events bool notify(QObject*, QEvent*) override; bool event(QEvent* event) override; bool eventFilter(QObject* object, QEvent* event) override; void postLambdaEvent(const std::function<void()>& f) override; void sendLambdaEvent(const std::function<void()>& f) override; virtual void pushPostUpdateLambda(void* key, const std::function<void()>& func) override; // Camera Camera& getCamera() { return _myCamera; } const Camera& getCamera() const { return _myCamera; } // Represents the current view frustum of the avatar. void copyViewFrustum(ViewFrustum& viewOut) const; // Represents the view frustum of the current rendering pass, // which might be different from the viewFrustum, i.e. shadowmap // passes, mirror window passes, etc void copyDisplayViewFrustum(ViewFrustum& viewOut) const; void updateCamera(RenderArgs& renderArgs, float deltaTime); void updateSecondaryCameraViewFrustum(); const ConicalViewFrustums& getConicalViews() const override { return _conicalViews; } float getFieldOfView() { return _fieldOfView.get(); } void setFieldOfView(float fov); bool getCameraClippingEnabled() { return _cameraClippingEnabled.get(); } void setCameraClippingEnabled(bool enabled); void updateMyAvatarLookAtPosition(float deltaTime); // Entities QSharedPointer<EntityTreeRenderer> getEntities() const { return DependencyManager::get<EntityTreeRenderer>(); } EntityTreePointer getEntityClipboard() const { return _entityClipboard; } const OctreePacketProcessor& getOctreePacketProcessor() const { return *_octreeProcessor; } std::shared_ptr<EntityEditPacketSender> getEntityEditPacketSender() { return _entityEditSender; } void setMaxOctreePacketsPerSecond(int maxOctreePPS); int getMaxOctreePacketsPerSecond() const { return _maxOctreePPS; } bool isMissingSequenceNumbers() { return _isMissingSequenceNumbers; } NodeToOctreeSceneStats* getOcteeSceneStats() { return _octreeProcessor->getOctreeSceneStats(); } // Assets virtual bool canAcceptURL(const QString& url) const override; virtual bool acceptURL(const QString& url, bool defaultUpload = false) override; // Physics bool isPhysicsEnabled() const { return _physicsEnabled; } PhysicsEnginePointer getPhysicsEngine() { return _physicsEngine; } const GameWorkload& getGameWorkload() const { return _gameWorkload; } float getNumCollisionObjects() const { return _physicsEngine ? _physicsEngine->getNumCollisionObjects() : 0; } void saveNextPhysicsStats(QString filename) { _physicsEngine->saveNextPhysicsStats(filename); } // Avatar virtual glm::vec3 getAvatarPosition() const override { return getMyAvatar()->getWorldPosition(); } void clearAvatarOverrideUrl() { _avatarOverrideUrl = QUrl(); _saveAvatarOverrideUrl = false; } QUrl getAvatarOverrideUrl() { return _avatarOverrideUrl; } bool getSaveAvatarOverrideUrl() { return _saveAvatarOverrideUrl; } int getOtherAvatarsReplicaCount() { return DependencyManager::get<AvatarHashMap>()->getReplicaCount(); } void setOtherAvatarsReplicaCount(int count) { DependencyManager::get<AvatarHashMap>()->setReplicaCount(count); } // Snapshots using SnapshotOperator = std::tuple<std::function<void(const QImage&)>, float, bool>; void addSnapshotOperator(const SnapshotOperator& snapshotOperator); bool takeSnapshotOperators(std::queue<SnapshotOperator>& snapshotOperators); void takeSnapshot(bool notify, bool includeAnimated = false, float aspectRatio = 0.0f, const QString& filename = QString()); void takeSecondaryCameraSnapshot(const bool& notify, const QString& filename = QString()); void takeSecondaryCamera360Snapshot(const glm::vec3& cameraPosition, const bool& cubemapOutputFormat, const bool& notify, const QString& filename = QString()); void shareSnapshot(const QString& filename, const QUrl& href = QUrl("")); #if defined(Q_OS_ANDROID) void beforeEnterBackground(); void enterBackground(); void enterForeground(); void toggleAwayMode();#endif signals: void svoImportRequested(const QString& url); void fullAvatarURLChanged(const QString& newValue, const QString& modelName); void beforeAboutToQuit(); void activeDisplayPluginChanged(); void uploadRequest(QString path); void interstitialModeChanged(bool isInInterstitialMode); void loginDialogFocusEnabled(); void loginDialogFocusDisabled(); void miniTabletEnabledChanged(bool enabled); void awayStateWhenFocusLostInVRChanged(bool enabled); void darkThemePreferenceChanged(bool useDarkTheme); void menuBarVisibilityChanged(bool visible); public slots: void updateThreadPoolCount() const; static void gotoTutorial(); void goToErrorDomainURL(QUrl errorDomainURL); void handleLocalServerConnection() const; void readArgumentsFromLocalSocket() const; void showUrlHandler(const QUrl& url); #if (PR_BUILD || DEV_BUILD) void sendWrongProtocolVersionsSignature(bool checked) { ::sendWrongProtocolVersionsSignature(checked); }#endif void hmdVisibleChanged(bool visible); void reloadResourceCaches(); void updateHeartbeat() const; static void deadlockApplication(); static void unresponsiveApplication(); // cause main thread to be unresponsive for 35 seconds void crashOnShutdown(); // used to test "shutdown" crash annotation. void rotationModeChanged() const; void setIsServerlessMode(bool serverlessDomain); std::map<QString, QString> prepareServerlessDomainContents(QUrl domainURL, QByteArray data); void loadServerlessDomain(QUrl domainURL); void loadErrorDomain(QUrl domainURL); void setIsInterstitialMode(bool interstitialMode); void updateVerboseLogging(); void setCachebustRequire(); QString getGraphicsCardType(); bool gpuTextureMemSizeStable(); Q_INVOKABLE SharedSoundPointer getSampleSound() const { return _sampleSound; } static void runTests(); // UI void showDialog(const QUrl& widgetUrl, const QUrl& tabletUrl, const QString& name) const; Q_INVOKABLE void loadDialog(); Q_INVOKABLE void loadScriptURLDialog() const; void toggleLogDialog(); void recreateLogWindow(int); void toggleEntityScriptServerLogDialog(); Q_INVOKABLE void showAssetServerWidget(QString filePath = ""); Q_INVOKABLE void loadAddAvatarBookmarkDialog() const; Q_INVOKABLE void loadAvatarBrowser() const; void showLoginScreen(); static void showHelp(); void updateSystemTabletMode(); void captureMouseChanged(bool captureMouse); void toggleOverlays(); void setOverlaysVisible(bool visible); Q_INVOKABLE void centerUI() { _overlayConductor.centerUI(); } void addAssetToWorldMessageClose(); void loadLODToolsDialog(); void loadEntityStatisticsDialog(); void loadDomainConnectionDialog(); void showScriptLogs(); const QString getPreferredCursor() const { return _preferredCursor.get(); } void setPreferredCursor(const QString& cursor); bool getDarkThemePreference() const { return _darkTheme.get(); } void setDarkThemePreference(bool value); bool getMenuBarVisible() const { return _menuBarVisible.get(); } void setMenuBarVisible(bool visible); /** * @brief Shows/hides VR keyboard input for Overlay windows * * This is used by QML scripts to show and hide VR keyboard. Unlike JS API Keyboard.raised = true, * with showVRKeyboardForHudUI the input is passed to the active window on the overlay first. * * @param show * If set to true, then keyboard is shown, for false it's hidden. */ Q_INVOKABLE void showVRKeyboardForHudUI(bool show); // Plugins void resetSensors(bool andReload = false); // Entities QVector<EntityItemID> pasteEntities(const QString& entityHostType, float x, float y, float z); bool exportEntities(const QString& filename, const QVector<QUuid>& entityIDs, const glm::vec3* givenOffset = nullptr, const QVariantMap& options = QVariantMap()); bool exportEntities(const QString& filename, float x, float y, float z, float scale, const QVariantMap& options = QVariantMap()); bool importEntities(const QString& url, const bool isObservable = true, const qint64 callerId = -1); void setKeyboardFocusHighlight(const glm::vec3& position, const glm::quat& rotation, const glm::vec3& dimensions);Lines 1–500 of 964. Load more
// // Application.h // interface/src // // Created by Andrzej Kapolka on 5/10/13. // Copyright 2013 High Fidelity, Inc. // Copyright 2020 Vircadia contributors. // Copyright 2022-2023 Overte e.V. // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // SPDX-License-Identifier: Apache-2.0 // #ifndef hifi_Application_h #define hifi_Application_h #include <QtWidgets/QApplication> #include <AbstractScriptingServicesInterface.h> #include <AbstractUriHandler.h> #include <AbstractViewStateInterface.h> #include <AvatarHashMap.h> #include <EntityEditPacketSender.h> #include <ModerationFlags.h> #include <OctreeQuery.h> #include <PhysicsEngine.h> #include <ShapeManager.h> #include <TouchEvent.h> #include <ui-plugins/PluginContainer.h> #include "avatar/MyAvatar.h" #include "ConnectionMonitor.h" #include "CursorManager.h" #include "FancyCamera.h" #include "graphics/GraphicsEngine.h" #include "LoginStateManager.h" #include "octree/OctreePacketProcessor.h" #include "PerformanceManager.h" #include "RefreshRateManager.h" #include "scripting/DialogsManagerScriptingInterface.h" #include "ui/ApplicationOverlay.h" #include "ui/OverlayConductor.h" #include "ui/overlays/Overlays.h" #include "VisionSqueeze.h" #include "workload/GameWorkload.h" #ifndef USE_GL #include "VKCanvas.h" #endif class ArchiveDownloadInterface; class AudioInjector; class CompositorHelper; class ControllerScriptingInterface; class DiscordPresence; class EntityScriptServerLogDialog; class FileLogger; class GLCanvas; class KeyboardMouseDevice; class LogDialog; class MainWindow; class ModalDialogListener; class OffscreenUi; class TouchscreenDevice; class TouchscreenVirtualPadDevice; class QCommandLineParser; class QGestureEvent; class QQmlContext; class QQuickItem; namespace controller { class StateController; } class Application; #if defined(qApp) #undef qApp #endif #define qApp (static_cast<Application*>(QCoreApplication::instance())) class Application : public QApplication, public AbstractViewStateInterface, public AbstractScriptingServicesInterface, public AbstractUriHandler, public PluginContainer { Q_OBJECT public: Application( int& argc, char** argv, QElapsedTimer& startup_time ); ~Application(); /** * @brief Initialize everything * * This is a QApplication, and for Qt reasons it's desirable to create this object * as early as possible. Without that some Qt functions don't work, like QCoreApplication::applicationDirPath() * * So we keep the constructor as minimal as possible, and do the rest of the work in * this function. */ void initialize(const QCommandLineParser &parser); MainWindow* getWindow() const { return _window; } virtual QThread* getMainThread() override { return thread(); } bool isAboutToQuit() const { return _aboutToQuit; } bool isServerlessMode() const; bool isInterstitialMode() const { return _interstitialMode; } bool failedToConnectToEntityServer() const { return _failedToConnectToEntityServer; } void setPreviousSessionCrashed(bool value) { _previousSessionCrashed = value; } // Return an HTTP User-Agent string with OS and device information. Q_INVOKABLE QString getUserAgent(); PerformanceManager& getPerformanceManager() { return _performanceManager; } RefreshRateManager& getRefreshRateManager() { return _refreshRateManager; } float getGameLoopRate() const { return _gameLoopCounter.rate(); } #ifndef Q_OS_ANDROID FileLogger* getLogger() const { return _logger; } #endif bool getUseDiscordPresence() const { return _useDiscordPresence.get(); } void setUseDiscordPresence(bool enable); QString getPreviousScriptLocation() { return _previousScriptLocation.get(); } void setPreviousScriptLocation(const QString& previousScriptLocation) { _previousScriptLocation.set(previousScriptLocation); } void replaceDomainContent(const QString& url, const QString& itemName); void openDirectory(const QString& path); void overrideEntry() { _overrideEntry = true; } void forceDisplayName(const QString& displayName) { getMyAvatar()->setDisplayName(displayName); } void forceLoginWithTokens(const QString& tokens); void setConfigFileURL(const QString& fileUrl); void loadAvatarScripts(const QVector<QString>& urls); void unloadAvatarScripts(); Q_INVOKABLE void copyToClipboard(const QString& text); Q_INVOKABLE void setMinimumGPUTextureMemStabilityCount(int stabilityCount) { _minimumGPUTextureMemSizeStabilityCount = stabilityCount; } virtual ControllerScriptingInterface* getControllerScriptingInterface() { return _controllerScriptingInterface; } virtual void registerScriptEngineWithApplicationServices(ScriptManagerPointer& scriptManager) override; // used by preferences and HMDScriptingInterface... VisionSqueeze& getVisionSqueeze() { return _visionSqueeze; } // UI virtual ui::Menu* getPrimaryMenu() override; virtual void showDisplayPluginsTools(bool show) override; #ifdef USE_GL virtual GLWidget* getPrimaryWidget() override; #else virtual VKWidget* getPrimaryWidget() override; #endif virtual MainWindow* getPrimaryWindow() override; virtual QOpenGLContext* getPrimaryContext() override; virtual bool isForeground() const override; bool hasFocus() const; void setFocus(); void raise(); void showCursor(const Cursor::Icon& cursor); Overlays& getOverlays() { return _overlays; } ApplicationOverlay& getApplicationOverlay() { return *_applicationOverlay; } const ApplicationOverlay& getApplicationOverlay() const { return *_applicationOverlay; } CompositorHelper& getApplicationCompositor() const; virtual PickRay computePickRay(float x, float y) const override; static void setupQmlSurface(QQmlContext* surfaceContext, bool setAdditionalContextProperties); float getHMDTabletScale() { return _hmdTabletScale.get(); } void setHMDTabletScale(float hmdTabletScale) { _hmdTabletScale.set(hmdTabletScale); } float getDesktopTabletScale() { return _desktopTabletScale.get(); } void setDesktopTabletScale(float desktopTabletScale) { _desktopTabletScale.set(desktopTabletScale); } bool getDesktopTabletBecomesToolbarSetting() { return _desktopTabletBecomesToolbarSetting.get(); } void setDesktopTabletBecomesToolbarSetting(bool value); bool getHmdTabletBecomesToolbarSetting() { return _hmdTabletBecomesToolbarSetting.get(); } void setHmdTabletBecomesToolbarSetting(bool value); bool getLogWindowOnTopSetting() { return _keepLogWindowOnTop.get(); } void setLogWindowOnTopSetting(bool keepOnTop) { _keepLogWindowOnTop.set(keepOnTop); } bool getPreferStylusOverLaser() { return _preferStylusOverLaserSetting.get(); } void setPreferStylusOverLaser(bool value) { _preferStylusOverLaserSetting.set(value); } bool getPreferAvatarFingerOverStylus() { return _preferAvatarFingerOverStylusSetting.get(); } void setPreferAvatarFingerOverStylus(bool value) { _preferAvatarFingerOverStylusSetting.set(value); } void setMouseCaptureVR(bool value); bool getMouseCaptureVR(); bool getMiniTabletEnabled() { return _miniTabletEnabledSetting.get(); } void setMiniTabletEnabled(bool enabled); float getSettingConstrainToolbarPosition() { return _constrainToolbarPosition.get(); } void setSettingConstrainToolbarPosition(bool setting); float getAwayStateWhenFocusLostInVREnabled() { return _awayStateWhenFocusLostInVREnabled.get(); } void setAwayStateWhenFocusLostInVREnabled(bool setting); QUuid getTabletScreenID() const; QUuid getTabletHomeButtonID() const; QUuid getTabletFrameID() const; QVector<QUuid> getTabletIDs() const; void confirmConnectWithoutAvatarEntities(); bool getLoginDialogPoppedUp() const { return _loginDialogPoppedUp; } void createLoginDialog(); void updateLoginDialogPosition(); void createAvatarInputsBar(); void destroyAvatarInputsBar(); // Plugins /** * @brief Initialize the plugin manager * * This both does the initial startup and parses arguments. This * is necessary because the plugin manager's options must be set * before any usage of it is made, or they won't apply. * * @param parser */ void initializePluginManager(const QCommandLineParser& parser); virtual void requestReset() override { resetSensors(false); } virtual bool makeRenderingContextCurrent() override { return true; } static void shutdownPlugins(); void initializeDisplayPlugins(); virtual DisplayPluginPointer getActiveDisplayPlugin() const override; void setActiveDisplayPlugin(const QString& pluginName); glm::uvec2 getUiSize() const; QRect getRecommendedHUDRect() const; glm::vec2 getDeviceSize() const; bool isThrottleRendering() const; float getTargetRenderFrameRate() const; // frames/second // Check if a headset is connected bool hasRiftControllers(); bool hasViveControllers(); // the isHMDMode is true whenever we use the interface from an HMD and not a standard flat display // rendering of several elements depend on that // TODO: carry that information on the Camera as a setting virtual bool isHMDMode() const override; glm::mat4 getHMDSensorPose() const; glm::mat4 getEyeOffset(int eye) const; glm::mat4 getEyeProjection(int eye) const; // Graphics void initializeGL(); void initializeRenderEngine(); void initializeUi(); void resizeGL(); glm::uvec2 getCanvasSize() const; float getRenderResolutionScale() const; render::ScenePointer getMain3DScene() override { return _graphicsEngine->getRenderScene(); } render::EnginePointer getRenderEngine() override { return _graphicsEngine->getRenderEngine(); } gpu::ContextPointer getGPUContext() const { return _graphicsEngine->getGPUContext(); } float getRenderLoopRate() const { return _graphicsEngine->getRenderLoopRate(); } // Events bool notify(QObject*, QEvent*) override; bool event(QEvent* event) override; bool eventFilter(QObject* object, QEvent* event) override; void postLambdaEvent(const std::function<void()>& f) override; void sendLambdaEvent(const std::function<void()>& f) override; virtual void pushPostUpdateLambda(void* key, const std::function<void()>& func) override; // Camera Camera& getCamera() { return _myCamera; } const Camera& getCamera() const { return _myCamera; } // Represents the current view frustum of the avatar. void copyViewFrustum(ViewFrustum& viewOut) const; // Represents the view frustum of the current rendering pass, // which might be different from the viewFrustum, i.e. shadowmap // passes, mirror window passes, etc void copyDisplayViewFrustum(ViewFrustum& viewOut) const; void updateCamera(RenderArgs& renderArgs, float deltaTime); void updateSecondaryCameraViewFrustum(); const ConicalViewFrustums& getConicalViews() const override { return _conicalViews; } float getFieldOfView() { return _fieldOfView.get(); } void setFieldOfView(float fov); bool getCameraClippingEnabled() { return _cameraClippingEnabled.get(); } void setCameraClippingEnabled(bool enabled); void updateMyAvatarLookAtPosition(float deltaTime); // Entities QSharedPointer<EntityTreeRenderer> getEntities() const { return DependencyManager::get<EntityTreeRenderer>(); } EntityTreePointer getEntityClipboard() const { return _entityClipboard; } const OctreePacketProcessor& getOctreePacketProcessor() const { return *_octreeProcessor; } std::shared_ptr<EntityEditPacketSender> getEntityEditPacketSender() { return _entityEditSender; } void setMaxOctreePacketsPerSecond(int maxOctreePPS); int getMaxOctreePacketsPerSecond() const { return _maxOctreePPS; } bool isMissingSequenceNumbers() { return _isMissingSequenceNumbers; } NodeToOctreeSceneStats* getOcteeSceneStats() { return _octreeProcessor->getOctreeSceneStats(); } // Assets virtual bool canAcceptURL(const QString& url) const override; virtual bool acceptURL(const QString& url, bool defaultUpload = false) override; // Physics bool isPhysicsEnabled() const { return _physicsEnabled; } PhysicsEnginePointer getPhysicsEngine() { return _physicsEngine; } const GameWorkload& getGameWorkload() const { return _gameWorkload; } float getNumCollisionObjects() const { return _physicsEngine ? _physicsEngine->getNumCollisionObjects() : 0; } void saveNextPhysicsStats(QString filename) { _physicsEngine->saveNextPhysicsStats(filename); } // Avatar virtual glm::vec3 getAvatarPosition() const override { return getMyAvatar()->getWorldPosition(); } void clearAvatarOverrideUrl() { _avatarOverrideUrl = QUrl(); _saveAvatarOverrideUrl = false; } QUrl getAvatarOverrideUrl() { return _avatarOverrideUrl; } bool getSaveAvatarOverrideUrl() { return _saveAvatarOverrideUrl; } int getOtherAvatarsReplicaCount() { return DependencyManager::get<AvatarHashMap>()->getReplicaCount(); } void setOtherAvatarsReplicaCount(int count) { DependencyManager::get<AvatarHashMap>()->setReplicaCount(count); } // Snapshots using SnapshotOperator = std::tuple<std::function<void(const QImage&)>, float, bool>; void addSnapshotOperator(const SnapshotOperator& snapshotOperator); bool takeSnapshotOperators(std::queue<SnapshotOperator>& snapshotOperators); void takeSnapshot(bool notify, bool includeAnimated = false, float aspectRatio = 0.0f, const QString& filename = QString()); void takeSecondaryCameraSnapshot(const bool& notify, const QString& filename = QString()); void takeSecondaryCamera360Snapshot(const glm::vec3& cameraPosition, const bool& cubemapOutputFormat, const bool& notify, const QString& filename = QString()); void shareSnapshot(const QString& filename, const QUrl& href = QUrl("")); #if defined(Q_OS_ANDROID) void beforeEnterBackground(); void enterBackground(); void enterForeground(); void toggleAwayMode(); #endif signals: void svoImportRequested(const QString& url); void fullAvatarURLChanged(const QString& newValue, const QString& modelName); void beforeAboutToQuit(); void activeDisplayPluginChanged(); void uploadRequest(QString path); void interstitialModeChanged(bool isInInterstitialMode); void loginDialogFocusEnabled(); void loginDialogFocusDisabled(); void miniTabletEnabledChanged(bool enabled); void awayStateWhenFocusLostInVRChanged(bool enabled); void darkThemePreferenceChanged(bool useDarkTheme); void menuBarVisibilityChanged(bool visible); public slots: void updateThreadPoolCount() const; static void gotoTutorial(); void goToErrorDomainURL(QUrl errorDomainURL); void handleLocalServerConnection() const; void readArgumentsFromLocalSocket() const; void showUrlHandler(const QUrl& url); #if (PR_BUILD || DEV_BUILD) void sendWrongProtocolVersionsSignature(bool checked) { ::sendWrongProtocolVersionsSignature(checked); } #endif void hmdVisibleChanged(bool visible); void reloadResourceCaches(); void updateHeartbeat() const; static void deadlockApplication(); static void unresponsiveApplication(); // cause main thread to be unresponsive for 35 seconds void crashOnShutdown(); // used to test "shutdown" crash annotation. void rotationModeChanged() const; void setIsServerlessMode(bool serverlessDomain); std::map<QString, QString> prepareServerlessDomainContents(QUrl domainURL, QByteArray data); void loadServerlessDomain(QUrl domainURL); void loadErrorDomain(QUrl domainURL); void setIsInterstitialMode(bool interstitialMode); void updateVerboseLogging(); void setCachebustRequire(); QString getGraphicsCardType(); bool gpuTextureMemSizeStable(); Q_INVOKABLE SharedSoundPointer getSampleSound() const { return _sampleSound; } static void runTests(); // UI void showDialog(const QUrl& widgetUrl, const QUrl& tabletUrl, const QString& name) const; Q_INVOKABLE void loadDialog(); Q_INVOKABLE void loadScriptURLDialog() const; void toggleLogDialog(); void recreateLogWindow(int); void toggleEntityScriptServerLogDialog(); Q_INVOKABLE void showAssetServerWidget(QString filePath = ""); Q_INVOKABLE void loadAddAvatarBookmarkDialog() const; Q_INVOKABLE void loadAvatarBrowser() const; void showLoginScreen(); static void showHelp(); void updateSystemTabletMode(); void captureMouseChanged(bool captureMouse); void toggleOverlays(); void setOverlaysVisible(bool visible); Q_INVOKABLE void centerUI() { _overlayConductor.centerUI(); } void addAssetToWorldMessageClose(); void loadLODToolsDialog(); void loadEntityStatisticsDialog(); void loadDomainConnectionDialog(); void showScriptLogs(); const QString getPreferredCursor() const { return _preferredCursor.get(); } void setPreferredCursor(const QString& cursor); bool getDarkThemePreference() const { return _darkTheme.get(); } void setDarkThemePreference(bool value); bool getMenuBarVisible() const { return _menuBarVisible.get(); } void setMenuBarVisible(bool visible); /** * @brief Shows/hides VR keyboard input for Overlay windows * * This is used by QML scripts to show and hide VR keyboard. Unlike JS API Keyboard.raised = true, * with showVRKeyboardForHudUI the input is passed to the active window on the overlay first. * * @param show * If set to true, then keyboard is shown, for false it's hidden. */ Q_INVOKABLE void showVRKeyboardForHudUI(bool show); // Plugins void resetSensors(bool andReload = false); // Entities QVector<EntityItemID> pasteEntities(const QString& entityHostType, float x, float y, float z); bool exportEntities(const QString& filename, const QVector<QUuid>& entityIDs, const glm::vec3* givenOffset = nullptr, const QVariantMap& options = QVariantMap()); bool exportEntities(const QString& filename, float x, float y, float z, float scale, const QVariantMap& options = QVariantMap()); bool importEntities(const QString& url, const bool isObservable = true, const qint64 callerId = -1); void setKeyboardFocusHighlight(const glm::vec3& position, const glm::quat& rotation, const glm::vec3& dimensions);