1// Copyright (C) 2017 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#include "qscene2d.h"
5#include "qscene2d_p.h"
6#include <private/qrenderaspect_p.h>
7#include "scene2d_p.h"
8#include "scene2dmanager_p.h"
9#include "scene2devent_p.h"
10
11#include <Qt3DCore/qentity.h>
12
13QT_BEGIN_NAMESPACE
14
15using namespace Qt3DCore;
16
17namespace Qt3DRender {
18
19namespace Quick {
20
21/*!
22 \namespace Qt3DRender::Quick
23 \inmodule Qt3DScene2D
24 \brief Internal namespace to import QML types.
25*/
26
27/*!
28 \class Qt3DRender::Quick::QScene2D
29 \inheaderfile Qt3DQuickScene2D/QScene2D
30 \inmodule Qt3DScene2D
31
32 \brief This class enables rendering qml into a texture, which then can be
33 used as a part of 3D scene.
34
35 This class uses QQuickRenderControl to render the given QQuickItem into an
36 offscreen surface, which is attached to a texture provided by the user. This allows the
37 component to directly render into the texture without intermediate copy and the user to
38 freely specify how the texture is used in the 3D scene.
39
40 The entities using the QScene2D can be associated with the class to enable interaction
41 with the item; if an entity has a QObjectPicker component, the pick events from that picker
42 are sent to the QScene2D and converted to mouse events and finally sent to the item.
43
44 \note Only mouse events are supported. The item does not support keyboard input.
45
46 \since 5.9
47*/
48
49/*!
50 \qmltype Scene2D
51 \inqmlmodule QtQuick.Scene2D
52 \since 5.9
53 \instantiates Qt3DRender::Quick::QScene2D
54
55 \brief This type enables rendering qml into a texture, which then can be
56 used as a part of 3D scene.
57
58 This object uses RenderControl to render the given Item into an
59 offscreen surface, which is attached to a texture provided by the user. This allows the
60 component to directly render into the texture without intermediate copy and the user to
61 freely specify how the texture is used in the 3D scene.
62
63 The entities using the Scene2D can be associated with the type to enable interaction
64 with the item; if an entity has an ObjectPicker component, the pick events from that picker
65 are sent to the Scene2D and converted to mouse events and finally sent to the item.
66
67 \note Only mouse events are supported. The item does not support keyboard input.
68
69 Usage:
70 \qml
71 Entity {
72 id: sceneRoot
73
74 // specify Scene2D inside the entity hierarchy
75 Scene2D {
76 // specify output
77 output: RenderTargetOutput {
78 attachmentPoint: RenderTargetOutput.Color0
79 texture: Texture2D {
80 id: textureId
81 width: 1024
82 height: 1024
83 format: Texture.RGBA8_UNorm
84 }
85 }
86 // specify entities
87 entities: [entityId]
88
89 // specify rendered content
90 Rectangle {
91 color: "red"
92 }
93 }
94
95 Entity {
96 id: entityId
97
98 property Material material: TextureMaterial {
99 texture: textureId
100 }
101 property ObjectPicker picker: ObjectPicker {
102 hoverEnabled: true
103 dragEnabled: true
104 }
105 ...
106
107 \endqml
108 */
109
110/*!
111 \enum QScene2D::RenderPolicy
112
113 This enum type describes types of render policies available.
114 \value Continuous The Scene2D is rendering continuously. This is the default render policy.
115 \value SingleShot The Scene2D renders to the texture only once after which the resources
116 allocated for rendering are released.
117*/
118
119/*!
120 \qmlproperty RenderTargetOutput QtQuick.Scene2D::Scene2D::output
121 Holds the RenderTargetOutput, which specifies where the Scene2D is rendering to.
122 */
123
124/*!
125 \qmlproperty enumeration QtQuick.Scene2D::Scene2D::renderPolicy
126 Holds the render policy of this Scene2D.
127
128 \list
129 \li Continuous The Scene2D is rendering continuously. This is the default render policy.
130 \li SingleShot The Scene2D renders to the texture only once after which the resources
131 allocated for rendering are released.
132 \endlist
133 */
134/*!
135 \qmlproperty Item QtQuick.Scene2D::Scene2D::item
136 Holds the Item, which is rendered by Scene2D to the texture.
137 */
138
139/*!
140 \qmlproperty bool QtQuick.Scene2D::Scene2D::mouseEnabled
141 Holds whether mouse events are enabled for the rendered item. The mouse events are
142 generated from object picking events of the entities added to the Scene2D.
143 Mouse is enabled by default.
144
145 \note Events sent to items are delayed by one frame due to object picking
146 happening in the backend.
147 */
148/*!
149 \qmlproperty list<Entity> QtQuick.Scene2D::Scene2D::entities
150 Holds the list of entities which are associated with the Scene2D object. If the
151 entities have ObjectPicker, the pick events from that entity are sent to Scene2D
152 and converted to mouse events.
153 */
154
155QScene2DPrivate::QScene2DPrivate()
156 : Qt3DCore::QNodePrivate()
157 , m_renderManager(new Scene2DManager(this))
158 , m_output(nullptr)
159{
160}
161
162QScene2DPrivate::~QScene2DPrivate()
163{
164 m_renderManager->cleanup();
165 delete m_renderManager;
166}
167
168
169/*!
170 The constructor creates a new QScene2D instance with the specified \a parent.
171 */
172QScene2D::QScene2D(Qt3DCore::QNode *parent)
173 : Qt3DCore::QNode(*new QScene2DPrivate, parent)
174{
175#ifdef QT_STATIC
176 static bool isInitialized = false;
177 if (!isInitialized) {
178 Qt3DRender::QRenderAspectPrivate::configurePlugin(QLatin1String("scene2d"));
179 }
180#endif
181}
182
183/*!
184 \property QScene2D::item
185 Holds the QQuickItem, which is rendered by QScene2D to the texture.
186 */
187QQuickItem* QScene2D::item() const
188{
189 Q_D(const QScene2D);
190 return d->m_renderManager->m_item;
191}
192
193void QScene2D::setItem(QQuickItem *item)
194{
195 Q_D(QScene2D);
196 if (d->m_renderManager->m_initialized) {
197 qWarning() << "Unable to set item after initialization.";
198 return;
199 }
200 if (d->m_renderManager->m_item != item) {
201 d->m_renderManager->setItem(item);
202 emit itemChanged(item);
203 }
204}
205
206/*!
207 \property QScene2D::renderPolicy
208
209 Holds the render policy of this Scene2D.
210 */
211QScene2D::RenderPolicy QScene2D::renderPolicy() const
212{
213 Q_D(const QScene2D);
214 return d->m_renderManager->m_renderPolicy;
215}
216
217void QScene2D::setRenderPolicy(QScene2D::RenderPolicy renderPolicy)
218{
219 Q_D(const QScene2D);
220 if (d->m_renderManager->m_renderPolicy != renderPolicy) {
221 d->m_renderManager->m_renderPolicy = renderPolicy;
222 emit renderPolicyChanged(policy: renderPolicy);
223 }
224}
225
226/*!
227 \property QScene2D::output
228 Holds the QRenderTargetOutput, which specifies where the QScene2D is
229 rendering to.
230 */
231Qt3DRender::QRenderTargetOutput *QScene2D::output() const
232{
233 Q_D(const QScene2D);
234 return d->m_output;
235}
236
237void QScene2D::setOutput(Qt3DRender::QRenderTargetOutput *output)
238{
239 Q_D(QScene2D);
240 if (d->m_output != output) {
241 if (d->m_output)
242 d->unregisterDestructionHelper(node: d->m_output);
243 d->m_output = output;
244 if (output)
245 d->registerDestructionHelper(node: output, func: &QScene2D::setOutput, d->m_output);
246 emit outputChanged(output);
247 }
248}
249
250bool QScene2D::isMouseEnabled() const
251{
252 Q_D(const QScene2D);
253 return d->m_renderManager->m_mouseEnabled;
254}
255
256/*!
257 Retrieve entities associated with the QScene2D.
258 */
259QList<Qt3DCore::QEntity *> QScene2D::entities() const
260{
261 Q_D(const QScene2D);
262 return d->m_entities;
263}
264
265/*!
266 Adds an \a entity to the the QScene2D object. If the entities have QObjectPicker,
267 the pick events from that entity are sent to QScene2D and converted to mouse events.
268*/
269void QScene2D::addEntity(Qt3DCore::QEntity *entity)
270{
271 Q_D(QScene2D);
272 if (!d->m_entities.contains(t: entity)) {
273 d->m_entities.append(t: entity);
274
275 d->registerDestructionHelper(node: entity, func: &QScene2D::removeEntity, d->m_entities);
276 d->update();
277 }
278}
279
280/*!
281 Removes an \a entity from the the QScene2D object.
282*/
283void QScene2D::removeEntity(Qt3DCore::QEntity *entity)
284{
285 Q_D(QScene2D);
286 if (d->m_entities.contains(t: entity)) {
287 d->m_entities.removeAll(t: entity);
288
289 d->unregisterDestructionHelper(node: entity);
290 d->update();
291 }
292}
293
294/*!
295 \property QScene2D::mouseEnabled
296 Holds whether mouse events are enabled for the rendered item. The mouse events are
297 generated from object picking events of the entities added to the QScene2D.
298 Mouse is enabled by default.
299
300 \note Events are delayed by one frame due to object picking happening in the backend.
301 */
302void QScene2D::setMouseEnabled(bool enabled)
303{
304 Q_D(QScene2D);
305 if (d->m_renderManager->m_mouseEnabled != enabled) {
306 d->m_renderManager->m_mouseEnabled = enabled;
307 emit mouseEnabledChanged(enabled);
308 }
309}
310
311
312} // namespace Quick
313} // namespace Qt3DRender
314
315QT_END_NAMESPACE
316
317#include "moc_qscene2d.cpp"
318

source code of qt3d/src/quick3d/quick3dscene2d/items/qscene2d.cpp