Qt 6.x
The Qt SDK
Loading...
Searching...
No Matches
qquickitemgrabresult.cpp
Go to the documentation of this file.
1// Copyright (C) 2016 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
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 <private/qtquickglobal_p.h>
6
8#include "qquickwindow.h"
9#include "qquickitem.h"
10#if QT_CONFIG(quick_shadereffect)
12#endif
13
14#include <QtQml/QQmlEngine>
15#include <QtQml/QQmlInfo>
16
17#include <private/qquickpixmapcache_p.h>
18#include <private/qquickitem_p.h>
19#include <private/qsgcontext_p.h>
20#include <private/qsgadaptationlayer_p.h>
21
23
25
27{
28public:
33 {
34 }
35
37 {
38 delete cacheEntry;
39 }
40
41 void ensureImageInCache() const {
42 if (url.isEmpty() && !image.isNull()) {
45 static uint counter = 0;
48 }
49 }
50
52
54
55 mutable QUrl url;
57
60
66};
67
138QQuickItemGrabResult::QQuickItemGrabResult(QObject *parent)
140{
141}
142
150// ### Qt 7: remove and keep only QUrl overload
158{
159 Q_D(const QQuickItemGrabResult);
160 if (fileName.startsWith(QLatin1String("file:/")))
161 return saveToFile(QUrl(fileName));
162 return d->image.save(fileName);
163}
164
172bool QQuickItemGrabResult::saveToFile(const QUrl &filePath) const
173{
174 Q_D(const QQuickItemGrabResult);
175 if (!filePath.isLocalFile()) {
176 qWarning() << "saveToFile can only save to a file on the local filesystem";
177 return false;
178 }
179 return d->image.save(filePath.toLocalFile());
180}
181
182#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
183#if QT_DEPRECATED_SINCE(5, 15)
189{
190 return std::as_const(*this).saveToFile(fileName);
191}
192#endif
193#endif // < Qt 6
194
196{
197 Q_D(const QQuickItemGrabResult);
198 d->ensureImageInCache();
199 return d->url;
200}
201
203{
204 Q_D(const QQuickItemGrabResult);
205 return d->image;
206}
207
212{
214 if (e->type() == Event_Grab_Completed) {
215 // JS callback
216 if (d->qmlEngine && d->callback.isCallable()) {
217 d->callback.call(QJSValueList() << d->qmlEngine->newQObject(this));
218 deleteLater();
219 } else {
220 Q_EMIT ready();
221 }
222 return true;
223 }
224 return QObject::event(e);
225}
226
227void QQuickItemGrabResult::setup()
228{
230 if (!d->item) {
231 disconnect(d->window.data(), &QQuickWindow::beforeSynchronizing, this, &QQuickItemGrabResult::setup);
232 disconnect(d->window.data(), &QQuickWindow::afterRendering, this, &QQuickItemGrabResult::render);
234 return;
235 }
236
237 QSGRenderContext *rc = QQuickWindowPrivate::get(d->window.data())->context;
238 d->texture = rc->sceneGraphContext()->createLayer(rc);
239 d->texture->setItem(QQuickItemPrivate::get(d->item)->itemNode());
240 d->itemSize = QSizeF(d->item->width(), d->item->height());
241}
242
243void QQuickItemGrabResult::render()
244{
246 if (!d->texture)
247 return;
248
249 d->texture->setRect(QRectF(0, d->itemSize.height(), d->itemSize.width(), -d->itemSize.height()));
250 const QSize minSize = QQuickWindowPrivate::get(d->window.data())->context->sceneGraphContext()->minimumFBOSize();
251 d->texture->setSize(QSize(qMax(minSize.width(), d->textureSize.width()),
252 qMax(minSize.height(), d->textureSize.height())));
253 d->texture->scheduleUpdate();
254 d->texture->updateTexture();
255 d->image = d->texture->toImage();
256
257 delete d->texture;
258 d->texture = nullptr;
259
260 disconnect(d->window.data(), &QQuickWindow::beforeSynchronizing, this, &QQuickItemGrabResult::setup);
261 disconnect(d->window.data(), &QQuickWindow::afterRendering, this, &QQuickItemGrabResult::render);
263}
264
266{
267 QSize size = targetSize;
268 if (size.isEmpty())
269 size = QSize(item->width(), item->height());
270
271 if (size.width() < 1 || size.height() < 1) {
272 qmlWarning(item) << "grabToImage: item has invalid dimensions";
273 return nullptr;
274 }
275
276 if (!item->window()) {
277 qmlWarning(item) << "grabToImage: item is not attached to a window";
278 return nullptr;
279 }
280
283 effectiveWindow = renderWindow;
284
285 if (!effectiveWindow->isVisible()) {
286 qmlWarning(item) << "grabToImage: item's window is not visible";
287 return nullptr;
288 }
289
292 d->item = item;
293 d->window = item->window();
294 d->textureSize = size;
295
297
298 // trigger sync & render
299 item->window()->update();
300
301 return result;
302}
303
323{
325 if (!result)
327
329 connect(window(), &QQuickWindow::afterRendering, result, &QQuickItemGrabResult::render, Qt::DirectConnection);
330
332}
333
368bool QQuickItem::grabToImage(const QJSValue &callback, const QSize &targetSize)
369{
370 QQmlEngine *engine = qmlEngine(this);
371 if (!engine) {
372 qmlWarning(this) << "grabToImage: item has no QML engine";
373 return false;
374 }
375
376 if (!callback.isCallable()) {
377 qmlWarning(this) << "grabToImage: 'callback' is not a function";
378 return false;
379 }
380
382 if (size.isEmpty())
383 size = QSize(width(), height());
384
385 if (size.width() < 1 || size.height() < 1) {
386 qmlWarning(this) << "grabToImage: item has invalid dimensions";
387 return false;
388 }
389
390 if (!window()) {
391 qmlWarning(this) << "grabToImage: item is not attached to a window";
392 return false;
393 }
394
396 if (!result)
397 return false;
398
400 connect(window(), &QQuickWindow::afterRendering, result, &QQuickItemGrabResult::render, Qt::DirectConnection);
401
403 d->qmlEngine = engine;
404 d->callback = callback;
405 return true;
406}
407
409
410#include "moc_qquickitemgrabresult.cpp"
static void postEvent(QObject *receiver, QEvent *event, int priority=Qt::NormalEventPriority)
\inmodule QtCore
Definition qcoreevent.h:45
Type
This enum type defines the valid event types in Qt.
Definition qcoreevent.h:51
\inmodule QtGui
Definition qimage.h:37
The QJSValue class acts as a container for Qt/JavaScript data types.
Definition qjsvalue.h:31
bool isCallable() const
Returns true if this QJSValue is a function, otherwise returns false.
Definition qjsvalue.cpp:445
\inmodule QtCore
Definition qobject.h:90
static QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
\threadsafe
Definition qobject.cpp:2823
virtual bool event(QEvent *event)
This virtual function receives events to an object and should return true if the event e was recogniz...
Definition qobject.cpp:1363
void deleteLater()
\threadsafe
Definition qobject.cpp:2352
\inmodule QtCore
Definition qpointer.h:18
T * data() const
Definition qpointer.h:56
The QQmlEngine class provides an environment for instantiating QML components.
Definition qqmlengine.h:57
QPointer< QQuickWindow > window
static QQuickItemGrabResult * create(QQuickItem *item, const QSize &size)
QUrl url
\qmlproperty url QtQuick::ItemGrabResult::url
void ready()
This signal is emitted when the grab has completed.
Q_INVOKABLE bool saveToFile(const QString &fileName) const
\qmlmethod bool QtQuick::ItemGrabResult::saveToFile(fileName)
QImage image
\qmlproperty variant QtQuick::ItemGrabResult::image
bool event(QEvent *) override
void refFromEffectItem(bool hide)
QSGTransformNode * itemNode()
static QQuickItemPrivate * get(QQuickItem *item)
The QQuickItem class provides the most basic of all visual items in \l {Qt Quick}.
Definition qquickitem.h:64
QSharedPointer< QQuickItemGrabResult > grabToImage(const QSize &targetSize=QSize())
Grabs the item into an in-memory image.
QQuickWindow * window() const
Returns the window in which this item is rendered.
qreal width
This property holds the width of this item.
Definition qquickitem.h:76
const QSize & targetSize
Definition qquickitem.h:302
qreal height
This property holds the height of this item.
Definition qquickitem.h:77
static const QLatin1String itemGrabberScheme
static QWindow * renderWindowFor(QQuickWindow *win, QPoint *offset=nullptr)
Returns the real window that win is being rendered to, if any.
static QQuickWindowPrivate * get(QQuickWindow *c)
QSGRenderContext * context
void beforeSynchronizing()
This signal is emitted before the scene graph is synchronized with the QML state.
void update()
Schedules the window to render another frame.
void afterRendering()
\qmlsignal QtQuick::Window::beforeRendering()
\inmodule QtCore\reentrant
Definition qrect.h:483
virtual QSGLayer * createLayer(QSGRenderContext *renderContext)=0
virtual QSize minimumFBOSize() const
QSGContext * sceneGraphContext() const
\inmodule QtCore
\inmodule QtCore
Definition qsize.h:207
\inmodule QtCore
Definition qsize.h:25
constexpr int height() const noexcept
Returns the height.
Definition qsize.h:132
constexpr int width() const noexcept
Returns the width.
Definition qsize.h:129
\macro QT_RESTRICTED_CAST_FROM_ASCII
Definition qstring.h:127
static QString number(int, int base=10)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qstring.cpp:7822
\inmodule QtCore
Definition qurl.h:94
bool isLocalFile() const
Definition qurl.cpp:3431
void setFragment(const QString &fragment, ParsingMode mode=TolerantMode)
Sets the fragment of the URL to fragment.
Definition qurl.cpp:2645
bool isEmpty() const
Returns true if the URL has no data; otherwise returns false.
Definition qurl.cpp:1888
void setScheme(const QString &scheme)
Sets the scheme of the URL to scheme.
Definition qurl.cpp:1959
void setPath(const QString &path, ParsingMode mode=DecodedMode)
Sets the path of the URL to path.
Definition qurl.cpp:2411
QString toLocalFile() const
Returns the path of this URL formatted as a local file path.
Definition qurl.cpp:3411
static auto fromValue(T &&value) noexcept(std::is_nothrow_copy_constructible_v< T > &&Private::CanUseInternalSpace< T >) -> std::enable_if_t< std::conjunction_v< std::is_copy_constructible< T >, std::is_destructible< T > >, QVariant >
Definition qvariant.h:531
\inmodule QtGui
Definition qwindow.h:63
double e
Combined button and popup list for selecting options.
@ DirectConnection
Definition image.cpp:4
QList< QJSValue > QJSValueList
Definition qjsvalue.h:22
#define qWarning
Definition qlogging.h:162
constexpr const T & qMax(const T &a, const T &b)
Definition qminmax.h:42
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLenum GLuint texture
GLuint counter
GLuint64EXT * result
[6]
QQmlEngine * qmlEngine(const QObject *obj)
Definition qqml.cpp:76
Q_QML_EXPORT QQmlInfo qmlWarning(const QObject *me)
QT_BEGIN_NAMESPACE const QEvent::Type Event_Grab_Completed
static QWindow * effectiveWindow(QWindow *window, QPoint *offset)
#define Q_EMIT
unsigned int uint
Definition qtypes.h:29
QObject::connect nullptr
myObject disconnect()
[26]
QGraphicsItem * item
view create()
QJSEngine engine
[0]
IUIAutomationTreeWalker __RPC__deref_out_opt IUIAutomationElement ** parent