Qt
Internal/Contributor docs for the Qt SDK. <b>Note:</b> These are NOT official API docs; those are found <a href='https://doc.qt.io/'>here</a>.
Loading...
Searching...
No Matches
qquickview.cpp
Go to the documentation of this file.
1// Copyright (C) 2016 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 "qquickview.h"
5#include "qquickview_p.h"
6
7#include "qquickwindow_p.h"
8#include "qquickitem_p.h"
10
11#include <QtQml/qqmlengine.h>
12#include <private/qqmlengine_p.h>
13#include <private/qv4qobjectwrapper_p.h>
14#include <QtCore/qbasictimer.h>
15
16#include <memory>
17
19
21{
22 Q_Q(QQuickView);
23
24 engine = e;
25
26 if (engine.isNull())
27 engine = new QQmlEngine(q);
28
30
32 engine.data()->setIncubationController(q->incubationController());
33
34 {
35 // The content item has CppOwnership policy (set in QQuickWindow). Ensure the presence of a JS
36 // wrapper so that the garbage collector can see the policy.
39 }
40}
41
43 : component(nullptr), resizeMode(QQuickView::SizeViewToRootObject), initialSize(0,0)
44{
45}
46
50
52{
53 if (!engine) {
54 qWarning() << "QQuickView: invalid qml engine.";
55 return Stop;
56 }
57
58 if (root)
59 delete root;
60 if (component) {
61 delete component;
62 component = nullptr;
63 }
65}
66
68{
69 if (executeHelper() == Stop)
70 return;
71 Q_Q(QQuickView);
72 if (!source.isEmpty()) {
74 if (!component->isLoading()) {
75 q->continueExecute();
76 } else {
78 q, SLOT(continueExecute()));
79 }
80 }
81}
82
84{
85 if (executeHelper() == Stop)
86 return;
87 Q_Q(QQuickView);
88
90 if (!component->isLoading()) {
91 q->continueExecute();
92 } else {
94 q, SLOT(continueExecute()));
95 }
96
97}
98
100 const QRectF &oldGeometry)
101{
102 Q_Q(QQuickView);
103 if (resizeItem == root && resizeMode == QQuickView::SizeViewToRootObject) {
104 // wait for both width and height to be changed
106 }
107 QQuickItemChangeListener::itemGeometryChanged(resizeItem, change, oldGeometry);
108}
109
148: QQuickWindow(*(new QQuickViewPrivate), parent)
149{
150 d_func()->init();
151}
152
159 : QQuickView(parent)
160{
162}
163
176
187 : QQuickWindow(*(new QQuickViewPrivate), parent)
188{
190 d_func()->init(engine);
191}
192
197 : QQuickWindow(*(new QQuickViewPrivate), control)
198{
199 d_func()->init();
201}
202
207{
208 // Ensure that the component is destroyed before the engine; the engine may
209 // be a child of the QQuickViewPrivate, and will be destroyed by its dtor
210 Q_D(QQuickView);
211 delete d->root;
212}
213
235{
236 Q_D(QQuickView);
237 d->source = url;
238 d->execute();
239}
240
255{
256 Q_D(QQuickView);
257 d->source = {}; // clear URL
258 d->execute(uri, typeName);
259}
260
274void QQuickView::setInitialProperties(const QVariantMap &initialProperties)
275{
276 Q_D(QQuickView);
277 d->initialProperties = initialProperties;
278}
279
286{
287 Q_D(QQuickView);
288 d->source = url;
289 d->component = component;
290
291 if (d->component && d->component->isError()) {
292 const QList<QQmlError> errorList = d->component->errors();
293 for (const QQmlError &error : errorList) {
294 QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
295 << error;
296 }
298 return;
299 }
300
301 if (!d->setRootObject(item))
302 delete item;
304}
305
312{
313 Q_D(const QQuickView);
314 return d->source;
315}
316
322{
323 Q_D(const QQuickView);
324 return d->engine ? const_cast<QQmlEngine *>(d->engine.data()) : nullptr;
325}
326
335{
336 Q_D(const QQuickView);
337 return d->engine ? d->engine.data()->rootContext() : nullptr;
338}
339
365{
366 Q_D(const QQuickView);
367 if (!d->engine)
368 return QQuickView::Error;
369
370 if (!d->component)
371 return QQuickView::Null;
372
373 if (d->component->status() == QQmlComponent::Ready && !d->root)
374 return QQuickView::Error;
375
376 return QQuickView::Status(d->component->status());
377}
378
383QList<QQmlError> QQuickView::errors() const
384{
385 Q_D(const QQuickView);
386 QList<QQmlError> errs;
387
388 if (d->component)
389 errs = d->component->errors();
390
391 if (!d->engine) {
393 error.setDescription(QLatin1String("QQuickView: invalid qml engine."));
394 errs << error;
395 } else if (d->component && d->component->status() == QQmlComponent::Ready && !d->root) {
397 error.setDescription(QLatin1String("QQuickView: invalid root object."));
398 errs << error;
399 }
400
401 return errs;
402}
403
418{
419 Q_D(QQuickView);
420 if (d->resizeMode == mode)
421 return;
422
423 if (d->root) {
424 if (d->resizeMode == SizeViewToRootObject) {
426 p->removeItemChangeListener(d, QQuickItemPrivate::Geometry);
427 }
428 }
429
430 d->resizeMode = mode;
431 if (d->root) {
432 d->initResize();
433 }
434}
435
437{
438 if (root) {
441 p->addItemChangeListener(this, QQuickItemPrivate::Geometry);
442 }
443 }
444 updateSize();
445}
446
448{
449 Q_Q(QQuickView);
450 if (!root)
451 return;
452
454 QSize newSize = QSize(root->width(), root->height());
455 if (newSize.isValid() && newSize != q->size()) {
456 q->resize(newSize);
457 }
459 bool needToUpdateWidth = !qFuzzyCompare(q->width(), root->width());
460 bool needToUpdateHeight = !qFuzzyCompare(q->height(), root->height());
461
462 if (needToUpdateWidth && needToUpdateHeight)
463 root->setSize(QSizeF(q->width(), q->height()));
464 else if (needToUpdateWidth)
465 root->setWidth(q->width());
466 else if (needToUpdateHeight)
467 root->setHeight(q->height());
468 }
469}
470
472{
474 int widthCandidate = -1;
475 int heightCandidate = -1;
476 if (root) {
477 widthCandidate = root->width();
478 heightCandidate = root->height();
479 }
480 if (widthCandidate > 0) {
481 rootObjectSize.setWidth(widthCandidate);
482 }
483 if (heightCandidate > 0) {
484 rootObjectSize.setHeight(heightCandidate);
485 }
486 return rootObjectSize;
487}
488
490{
491 Q_D(const QQuickView);
492 return d->resizeMode;
493}
494
498void QQuickView::continueExecute()
499{
500 Q_D(QQuickView);
501 disconnect(d->component, SIGNAL(statusChanged(QQmlComponent::Status)), this, SLOT(continueExecute()));
502
503 if (d->component->isError()) {
504 const QList<QQmlError> errorList = d->component->errors();
505 for (const QQmlError &error : errorList) {
506 QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
507 << error;
508 }
510 return;
511 }
512
513 std::unique_ptr<QObject> obj(d->initialProperties.empty()
514 ? d->component->create()
515 : d->component->createWithInitialProperties(d->initialProperties));
516
517 if (d->component->isError()) {
518 const QList<QQmlError> errorList = d->component->errors();
519 for (const QQmlError &error : errorList) {
520 QMessageLogger(error.url().toString().toLatin1().constData(), error.line(), nullptr).warning()
521 << error;
522 }
524 return;
525 }
526
527 // If we used loadFromModule, we might not have a URL so far.
528 // Thus, query the component to retrieve the associated URL, if any
529 if (d->source.isEmpty())
530 d->source = d->component->url();
531
532 if (d->setRootObject(obj.get()))
533 Q_UNUSED(obj.release());
535}
536
537
547{
548 Q_Q(QQuickView);
549 if (root == obj)
550 return true;
551
552 delete root;
553 if (obj == nullptr)
554 return true;
555
556 if (QQuickItem *sgItem = qobject_cast<QQuickItem *>(obj)) {
557 root = sgItem;
559 sgItem->setParentItem(q->QQuickWindow::contentItem());
560 QQml_setParent_noEvent(sgItem, q->QQuickWindow::contentItem());
562 if ((resizeMode == QQuickView::SizeViewToRootObject || q->width() <= 1 || q->height() <= 1) &&
563 initialSize != q->size()) {
564 q->resize(initialSize);
565 }
566 initResize();
567 return true;
568 }
569
570 if (qobject_cast<QWindow *>(obj)) {
571 qWarning() << "QQuickView does not support using a window as a root item." << Qt::endl
572 << Qt::endl
573 << "If you wish to create your root window from QML, consider using QQmlApplicationEngine instead." << Qt::endl;
574 return false;
575 }
576
577 qWarning() << "QQuickView only supports loading of root objects that derive from QQuickItem." << Qt::endl
578 << Qt::endl
579 << "Ensure your QML code is written for QtQuick 2, and uses a root that is or" << Qt::endl
580 << "inherits from QtQuick's Item (not a Timer, QtObject, etc)." << Qt::endl;
581 return false;
582}
583
590{
591 Q_D(QQuickView);
592 if (!e || e->timerId() == d->resizetimer.timerId()) {
593 d->updateSize();
594 d->resizetimer.stop();
595 }
596}
597
603{
604 Q_D(const QQuickView);
605 QSize rootObjectSize = d->rootObjectSize();
606 if (rootObjectSize.isEmpty()) {
607 return size();
608 } else {
609 return rootObjectSize;
610 }
611}
612
621{
622 Q_D(const QQuickView);
623 return d->initialSize;
624}
625
630{
631 Q_D(const QQuickView);
632 return d->root;
633}
634
641{
642 Q_D(QQuickView);
643 if (d->resizeMode == SizeRootObjectToView)
644 d->updateSize();
645
647}
648
654
660
666
672
678
679
681
682#include "moc_qquickview.cpp"
\inmodule QtCore
void start(int msec, QObject *obj)
\obsolete Use chrono overload instead.
QV4::ExecutionEngine * handle() const
Definition qjsengine.h:298
The QKeyEvent class describes a key event.
Definition qevent.h:424
\inmodule QtCore
Definition qlogging.h:72
void void Q_DECL_COLD_FUNCTION void warning(const char *msg,...) const Q_ATTRIBUTE_FORMAT_PRINTF(2
Logs a warning message specified with format msg.
Definition qlogging.cpp:625
\inmodule QtGui
Definition qevent.h:196
\inmodule QtCore
Definition qobject.h:103
static QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
\threadsafe
Definition qobject.cpp:2960
T * data() const noexcept
Definition qpointer.h:73
bool isNull() const noexcept
Definition qpointer.h:84
The QQmlComponent class encapsulates a QML component definition.
Status
\qmltype Component \instantiates QQmlComponent\inqmlmodule QtQml
bool isLoading() const
Returns true if status() == QQmlComponent::Loading.
The QQmlContext class defines a context within a QML engine.
Definition qqmlcontext.h:25
The QQmlEngine class provides an environment for instantiating QML components.
Definition qqmlengine.h:57
QQmlIncubationController * incubationController() const
Returns the currently set incubation controller, or 0 if no controller has been set.
static void setContextForObject(QObject *, QQmlContext *)
Sets the QQmlContext for the object to context.
void setIncubationController(QQmlIncubationController *)
Sets the engine's incubation controller.
QQmlContext * rootContext() const
Returns the engine's root context.
The QQmlError class encapsulates a QML error.
Definition qqmlerror.h:18
virtual void itemGeometryChanged(QQuickItem *, QQuickGeometryChange, const QRectF &)
static QQuickItemPrivate * get(QQuickItem *item)
The QQuickItem class provides the most basic of all visual items in \l {Qt Quick}.
Definition qquickitem.h:63
void setSize(const QSizeF &size)
void setFlag(Flag flag, bool enabled=true)
Enables the specified flag for this item if enabled is true; if enabled is false, the flag is disable...
void setHeight(qreal)
qreal width
This property holds the width of this item.
Definition qquickitem.h:75
qreal height
This property holds the height of this item.
Definition qquickitem.h:76
void setWidth(qreal)
The QQuickRenderControl class provides a mechanism for rendering the Qt Quick scenegraph onto an offs...
ExecuteState executeHelper()
QSize rootObjectSize() const
bool setRootObject(QObject *)
QBasicTimer resizetimer
QQuickView::ResizeMode resizeMode
QPointer< QQuickItem > root
void init(QQmlEngine *e=nullptr)
QPointer< QQmlEngine > engine
QQmlComponent * component
void itemGeometryChanged(QQuickItem *item, QQuickGeometryChange change, const QRectF &) override
The QQuickView class provides a window for displaying a Qt Quick user interface.
Definition qquickview.h:20
QQuickView(QWindow *parent=nullptr)
Constructs a QQuickView with the given parent.
void setContent(const QUrl &url, QQmlComponent *component, QObject *item)
~QQuickView() override
Destroys the QQuickView.
QUrl source
The URL of the source of the QML component.
Definition qquickview.h:24
ResizeMode resizeMode
whether the view should resize the window contents
Definition qquickview.h:22
void mousePressEvent(QMouseEvent *) override
\reimp
QList< QQmlError > errors() const
Return the list of errors that occurred during the last compile or create operation.
void keyReleaseEvent(QKeyEvent *) override
\reimp
void keyPressEvent(QKeyEvent *) override
\reimp
QSize initialSize() const
Returns the initial size of the root object.
void setResizeMode(ResizeMode)
void timerEvent(QTimerEvent *) override
Status status
The component's current \l{QQuickView::Status} {status}.
Definition qquickview.h:23
QQmlEngine * engine() const
Returns a pointer to the QQmlEngine used for instantiating QML Components.
QQmlContext * rootContext() const
This function returns the root of the context hierarchy.
ResizeMode
This enum specifies how to resize the view.
Definition qquickview.h:40
@ SizeViewToRootObject
Definition qquickview.h:40
@ SizeRootObjectToView
Definition qquickview.h:40
void resizeEvent(QResizeEvent *) override
void loadFromModule(QAnyStringView uri, QAnyStringView typeName)
Status
Specifies the loading status of the QQuickView.
Definition qquickview.h:45
void mouseMoveEvent(QMouseEvent *) override
\reimp
void setSource(const QUrl &)
Sets the source to the url, loads the QML component and instantiates it.
void setInitialProperties(const QVariantMap &initialProperties)
Sets the initial properties initialProperties with which the QML component gets initialized after cal...
QQuickItem * rootObject() const
Returns the view's root \l {QQuickItem} {item}.
void statusChanged(QQuickView::Status)
This signal is emitted when the component's current status changes.
QSize sizeHint() const
void mouseReleaseEvent(QMouseEvent *) override
\reimp
QQuickRootItem * contentItem
\qmltype Window \instantiates QQuickWindow \inqmlmodule QtQuick
void mousePressEvent(QMouseEvent *) override
\reimp
void resizeEvent(QResizeEvent *) override
\reimp
void mouseReleaseEvent(QMouseEvent *) override
\reimp
void mouseMoveEvent(QMouseEvent *) override
\reimp
void keyReleaseEvent(QKeyEvent *) override
\reimp
void keyPressEvent(QKeyEvent *) override
\reimp
\inmodule QtCore\reentrant
Definition qrect.h:484
The QResizeEvent class contains event parameters for resize events.
Definition qevent.h:548
\inmodule QtCore
Definition qsize.h:208
\inmodule QtCore
Definition qsize.h:25
constexpr void setWidth(int w) noexcept
Sets the width to the given width.
Definition qsize.h:136
constexpr bool isEmpty() const noexcept
Returns true if either of the width and height is less than or equal to 0; otherwise returns false.
Definition qsize.h:124
constexpr void setHeight(int h) noexcept
Sets the height to the given height.
Definition qsize.h:139
constexpr bool isValid() const noexcept
Returns true if both the width and height is equal to or greater than 0; otherwise returns false.
Definition qsize.h:127
\inmodule QtCore
Definition qcoreevent.h:366
int timerId() const
Returns the unique timer identifier, which is the same identifier as returned from QObject::startTime...
Definition qcoreevent.h:370
\inmodule QtCore
Definition qurl.h:94
\inmodule QtGui
Definition qwindow.h:63
QSize size() const override
Returns the size of the window excluding any window frame.
Definition qwindow.h:210
void statusChanged(QQmlComponent::Status status)
[1]
Definition qlogging.cpp:11
Combined button and popup list for selecting options.
QTextStream & endl(QTextStream &stream)
Writes '\n' to the stream and flushes the stream.
DBusConnection const char DBusError * error
bool qFuzzyCompare(qfloat16 p1, qfloat16 p2) noexcept
Definition qfloat16.h:333
#define qWarning
Definition qlogging.h:166
const char * typeName
#define SLOT(a)
Definition qobjectdefs.h:52
#define SIGNAL(a)
Definition qobjectdefs.h:53
GLenum mode
GLsizei GLsizei GLchar * source
GLhandleARB obj
[2]
GLdouble GLdouble GLdouble GLdouble q
Definition qopenglext.h:259
GLfloat GLfloat p
[1]
static qreal component(const QPointF &point, unsigned int i)
void QQml_setParent_noEvent(QObject *object, QObject *parent)
Makes the object a child of parent.
#define Q_ASSERT(cond)
Definition qrandom.cpp:47
QLatin1StringView QLatin1String
Definition qstringfwd.h:31
#define emit
#define Q_UNUSED(x)
QUrl url("example.com")
[constructor-url-reference]
QObject::connect nullptr
myObject disconnect()
[26]
QGraphicsItem * item
QJSEngine engine
[0]
static void ensureWrapper(ExecutionEngine *engine, QObject *object)