1/****************************************************************************
2**
3** Copyright (C) 2017 The Qt Company Ltd.
4** Contact: https://www.qt.io/licensing/
5**
6** This file is part of the examples of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:BSD$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and The Qt Company. For licensing terms
14** and conditions see https://www.qt.io/terms-conditions. For further
15** information use the contact form at https://www.qt.io/contact-us.
16**
17** BSD License Usage
18** Alternatively, you may use this file under the terms of the BSD license
19** as follows:
20**
21** "Redistribution and use in source and binary forms, with or without
22** modification, are permitted provided that the following conditions are
23** met:
24** * Redistributions of source code must retain the above copyright
25** notice, this list of conditions and the following disclaimer.
26** * Redistributions in binary form must reproduce the above copyright
27** notice, this list of conditions and the following disclaimer in
28** the documentation and/or other materials provided with the
29** distribution.
30** * Neither the name of The Qt Company Ltd nor the names of its
31** contributors may be used to endorse or promote products derived
32** from this software without specific prior written permission.
33**
34**
35** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
36** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
37** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
38** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
39** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
40** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
41** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
42** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
43** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
44** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
45** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
46**
47** $QT_END_LICENSE$
48**
49****************************************************************************/
50
51#include <QQuickWidget>
52#include <QQuickItem>
53#include <QQmlError>
54#include <QtWidgets>
55#include "fbitem.h"
56
57static bool optMultipleSample = false;
58static bool optCoreProfile = false;
59
60class MainWindow : public QMainWindow {
61 Q_OBJECT
62public:
63 MainWindow();
64
65private slots:
66 void quickWidgetStatusChanged(QQuickWidget::Status);
67 void sceneGraphError(QQuickWindow::SceneGraphError error, const QString &message);
68 void grabFramebuffer();
69 void renderToPixmap();
70 void grabToImage();
71 void createQuickWidgetsInTabs(QMdiArea *mdiArea);
72
73private:
74 QQuickWidget *m_quickWidget;
75};
76
77MainWindow::MainWindow()
78 : m_quickWidget(new QQuickWidget)
79{
80 QSurfaceFormat format;
81 if (optCoreProfile) {
82 format.setVersion(major: 4, minor: 4);
83 format.setProfile(QSurfaceFormat::CoreProfile);
84 }
85 if (optMultipleSample)
86 format.setSamples(4);
87 m_quickWidget->setFormat(format);
88
89 QMdiArea *centralWidget = new QMdiArea;
90
91 QLCDNumber *lcd = new QLCDNumber;
92 lcd->display(num: 1337);
93 lcd->setMinimumSize(minw: 250,minh: 100);
94 centralWidget->addSubWindow(widget: lcd);
95
96 QUrl source("qrc:quickwidget/rotatingsquare.qml");
97
98 connect(sender: m_quickWidget, signal: &QQuickWidget::statusChanged,
99 receiver: this, slot: &MainWindow::quickWidgetStatusChanged);
100 connect(sender: m_quickWidget, signal: &QQuickWidget::sceneGraphError,
101 receiver: this, slot: &MainWindow::sceneGraphError);
102 m_quickWidget->resize(w: 300,h: 300);
103 m_quickWidget->setResizeMode(QQuickWidget::SizeRootObjectToView );
104 m_quickWidget->setSource(source);
105
106 centralWidget->addSubWindow(widget: m_quickWidget);
107
108 setCentralWidget(centralWidget);
109
110 QMenu *fileMenu = menuBar()->addMenu(title: tr(s: "&File"));
111 fileMenu->addAction(text: tr(s: "Grab framebuffer"), object: this, slot: &MainWindow::grabFramebuffer);
112 fileMenu->addAction(text: tr(s: "Render to pixmap"), object: this, slot: &MainWindow::renderToPixmap);
113 fileMenu->addAction(text: tr(s: "Grab via grabToImage"), object: this, slot: &MainWindow::grabToImage);
114 fileMenu->addAction(text: tr(s: "Quit"), qApp, slot: &QCoreApplication::quit);
115
116 QMenu *windowMenu = menuBar()->addMenu(title: tr(s: "&Window"));
117 windowMenu->addAction(text: tr(s: "Add tab widget"), object: this,
118 slot: [this, centralWidget] { createQuickWidgetsInTabs(mdiArea: centralWidget); });
119}
120
121void MainWindow::createQuickWidgetsInTabs(QMdiArea *mdiArea)
122{
123 QTabWidget *tabWidget = new QTabWidget;
124
125 const QSize size(400, 400);
126
127 QQuickWidget *w = new QQuickWidget;
128 w->resize(size);
129 w->setResizeMode(QQuickWidget::SizeRootObjectToView);
130 w->setSource(QUrl("qrc:quickwidget/rotatingsquaretab.qml"));
131
132 tabWidget->addTab(widget: w, tr(s: "Plain Quick content"));
133
134 w = new QQuickWidget;
135 w->resize(size);
136 w->setResizeMode(QQuickWidget::SizeRootObjectToView);
137 w->setSource(QUrl("qrc:quickwidget/customgl.qml"));
138
139 tabWidget->addTab(widget: w, tr(s: "Custom OpenGL drawing"));
140
141 mdiArea->addSubWindow(widget: tabWidget);
142 tabWidget->show();
143}
144
145void MainWindow::quickWidgetStatusChanged(QQuickWidget::Status status)
146{
147 if (status == QQuickWidget::Error) {
148 QStringList errors;
149 const auto widgetErrors = m_quickWidget->errors();
150 for (const QQmlError &error : widgetErrors)
151 errors.append(t: error.toString());
152 statusBar()->showMessage(text: errors.join(QStringLiteral(", ")));
153 }
154}
155
156void MainWindow::sceneGraphError(QQuickWindow::SceneGraphError, const QString &message)
157{
158 statusBar()->showMessage(text: message);
159}
160
161template<class T> void saveToFile(QWidget *parent, T *saveable)
162{
163 QFileDialog fd(parent);
164 fd.setAcceptMode(QFileDialog::AcceptSave);
165 fd.setDefaultSuffix("png");
166 fd.selectFile(filename: "test.png");
167 if (fd.exec() == QDialog::Accepted)
168 saveable->save(fd.selectedFiles().first());
169}
170
171void MainWindow::grabFramebuffer()
172{
173 QImage image = m_quickWidget->grabFramebuffer();
174 saveToFile(parent: this, saveable: &image);
175}
176
177void MainWindow::renderToPixmap()
178{
179 QPixmap pixmap(m_quickWidget->size());
180 m_quickWidget->render(target: &pixmap);
181 saveToFile(parent: this, saveable: &pixmap);
182}
183
184void MainWindow::grabToImage()
185{
186 QFileDialog fd(this);
187 fd.setAcceptMode(QFileDialog::AcceptSave);
188 fd.setDefaultSuffix("png");
189 fd.selectFile(filename: "test_grabToImage.png");
190 if (fd.exec() == QDialog::Accepted) {
191 QMetaObject::invokeMethod(obj: m_quickWidget->rootObject(), member: "performLayerBasedGrab",
192 Q_ARG(QVariant, fd.selectedFiles().first()));
193 }
194}
195
196int main(int argc, char **argv)
197{
198 QApplication app(argc, argv);
199
200 QCoreApplication::setApplicationName("Qt QQuickWidget Example");
201 QCoreApplication::setOrganizationName("QtProject");
202 QCoreApplication::setApplicationVersion(QT_VERSION_STR);
203 QCommandLineParser parser;
204 parser.setApplicationDescription(QCoreApplication::applicationName());
205 parser.addHelpOption();
206 parser.addVersionOption();
207 QCommandLineOption multipleSampleOption("multisample", "Multisampling");
208 parser.addOption(commandLineOption: multipleSampleOption);
209 QCommandLineOption coreProfileOption("coreprofile", "Use core profile");
210 parser.addOption(commandLineOption: coreProfileOption);
211
212 parser.process(app);
213
214 optMultipleSample = parser.isSet(option: multipleSampleOption);
215 optCoreProfile = parser.isSet(option: coreProfileOption);
216
217 MainWindow mainWindow;
218 mainWindow.show();
219
220 return app.exec();
221}
222
223#include "main.moc"
224

source code of qtdeclarative/examples/quick/quickwidgets/quickwidget/main.cpp