Overte C++ Documentation
OffscreenSurface.h
1 //
2 // Created by Bradley Austin Davis on 2015-04-04
3 // Copyright 2015 High Fidelity, Inc.
4 //
5 // Distributed under the Apache License, Version 2.0.
6 // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
7 //
8 #pragma once
9 #ifndef hifi_qml_OffscreenSurface_h
10 #define hifi_qml_OffscreenSurface_h
11 
12 #include <atomic>
13 #include <queue>
14 #include <map>
15 #include <functional>
16 
17 #include <QtCore/QUrl>
18 #include <QtCore/QSize>
19 #include <QtCore/QPointF>
20 #include <QtCore/QTimer>
21 
22 #include <QtQml/QJSValue>
23 
24 class QWindow;
25 class QOpenGLContext;
26 class QQmlContext;
27 class QQmlEngine;
28 class QQmlComponent;
29 class QQuickWindow;
30 class QQuickItem;
31 class OffscreenQmlSharedObject;
32 class QQmlFileSelector;
33 
34 namespace hifi { namespace qml {
35 
36 namespace impl {
37 class SharedObject;
38 }
39 
40 using QmlContextCallback = ::std::function<void(QQmlContext*)>;
41 using QmlContextObjectCallback = ::std::function<void(QQmlContext*, QQuickItem*)>;
42 using QmlUrlValidator = std::function<bool(const QUrl&)>;
43 
44 class OffscreenSurface : public QObject {
45  Q_OBJECT
46 
47 public:
48  static const QmlContextObjectCallback DEFAULT_CONTEXT_OBJECT_CALLBACK;
49  static const QmlContextCallback DEFAULT_CONTEXT_CALLBACK;
50  static QmlUrlValidator validator;
51  using TextureAndFence = std::pair<uint32_t, void*>;
52  using MouseTranslator = std::function<QPoint(const QPointF&)>;
53 
54 
55  static const QmlUrlValidator& getUrlValidator() { return validator; }
56  static void setUrlValidator(const QmlUrlValidator& newValidator) { validator = newValidator; }
57  static void setSharedContext(QOpenGLContext* context);
58 
59  OffscreenSurface();
60  virtual ~OffscreenSurface();
61 
62  QSize size() const;
63  virtual void resize(const QSize& size);
64  void clearCache();
65 
66  void setMaxFps(uint8_t maxFps);
67  // Optional values for event handling
68  void setProxyWindow(QWindow* window);
69  void setMouseTranslator(const MouseTranslator& mouseTranslator) { _mouseTranslator = mouseTranslator; }
70 
71  void pause();
72  void resume();
73  bool isPaused() const;
74 
75  QQuickItem* getRootItem();
76  QQuickWindow* getWindow();
77  QObject* getEventHandler();
78  QQmlContext* getSurfaceContext();
79  QQmlFileSelector* getFileSelector();
80 
81  // Checks to see if a new texture is available. If one is, the function returns true and
82  // textureAndFence will be populated with the texture ID and a fence which will be signalled
83  // when the texture is safe to read.
84  // Returns false if no new texture is available
85  bool fetchTexture(TextureAndFence& textureAndFence);
86 
87  static std::function<void(uint32_t, void*)> getDiscardLambda();
88  static size_t getUsedTextureMemory();
89  QPointF mapToVirtualScreen(const QPointF& originalPoint);
90 
91  // For use from QML/JS
92  Q_INVOKABLE void load(const QUrl& qmlSource, QQuickItem* parent, const QJSValue& callback);
93 
94  // For use from C++
95  Q_INVOKABLE void load(const QUrl& qmlSource, const QmlContextObjectCallback& callback = DEFAULT_CONTEXT_OBJECT_CALLBACK);
96  Q_INVOKABLE void load(const QUrl& qmlSource,
97  bool createNewContext,
98  const QmlContextObjectCallback& callback = DEFAULT_CONTEXT_OBJECT_CALLBACK);
99  Q_INVOKABLE void load(const QString& qmlSourceFile,
100  const QmlContextObjectCallback& callback = DEFAULT_CONTEXT_OBJECT_CALLBACK);
101  Q_INVOKABLE void loadInNewContext(const QUrl& qmlSource,
102  const QmlContextObjectCallback& callback = DEFAULT_CONTEXT_OBJECT_CALLBACK,
103  const QmlContextCallback& contextCallback = DEFAULT_CONTEXT_CALLBACK);
104 
105 public slots:
106  virtual void onFocusObjectChanged(QObject* newFocus) {}
107 
108 signals:
109  void rootContextCreated(QQmlContext* rootContext);
110  void rootItemCreated(QQuickItem* rootContext);
111 
112 protected:
113  virtual void loadFromQml(const QUrl& qmlSource, QQuickItem* parent, const QJSValue& callback);
114  bool eventFilter(QObject* originalDestination, QEvent* event) override;
115  bool filterEnabled(QObject* originalDestination, QEvent* event) const;
116 
117  virtual void initializeEngine(QQmlEngine* engine);
118  virtual void loadInternal(const QUrl& qmlSource,
119  bool createNewContext,
120  QQuickItem* parent,
121  const QmlContextObjectCallback& callback,
122  const QmlContextCallback& contextCallback = DEFAULT_CONTEXT_CALLBACK) final;
123  virtual void finishQmlLoad(QQmlComponent* qmlComponent,
124  QQmlContext* qmlContext,
125  QQuickItem* parent,
126  const QmlContextObjectCallback& onQmlLoadedCallback) final;
127 
128  virtual void onRootCreated() {}
129  virtual void onItemCreated(QQmlContext* context, QQuickItem* newItem) {}
130  virtual void onRootContextCreated(QQmlContext* qmlContext) {}
131 
132  virtual QQmlContext* contextForUrl(const QUrl& qmlSource, QQuickItem* parent, bool forceNewContext);
133 
134 private:
135  MouseTranslator _mouseTranslator{ [](const QPointF& p) { return p.toPoint(); } };
136  friend class hifi::qml::impl::SharedObject;
137  impl::SharedObject* const _sharedObject;
138 };
139 
140 }} // namespace hifi::qml
141 
142 #endif