1/****************************************************************************
2**
3** Copyright (C) 2016 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 "scribblearea.h"
52
53#include <QMouseEvent>
54#include <QPainter>
55
56#if defined(QT_PRINTSUPPORT_LIB)
57#include <QtPrintSupport/qtprintsupportglobal.h>
58#if QT_CONFIG(printdialog)
59#include <QPrinter>
60#include <QPrintDialog>
61#endif
62#endif
63
64//! [0]
65ScribbleArea::ScribbleArea(QWidget *parent)
66 : QWidget(parent)
67{
68 setAttribute(Qt::WA_StaticContents);
69}
70//! [0]
71
72//! [1]
73bool ScribbleArea::openImage(const QString &fileName)
74//! [1] //! [2]
75{
76 QImage loadedImage;
77 if (!loadedImage.load(fileName))
78 return false;
79
80 QSize newSize = loadedImage.size().expandedTo(otherSize: size());
81 resizeImage(image: &loadedImage, newSize);
82 image = loadedImage;
83 modified = false;
84 update();
85 return true;
86}
87//! [2]
88
89//! [3]
90bool ScribbleArea::saveImage(const QString &fileName, const char *fileFormat)
91//! [3] //! [4]
92{
93 QImage visibleImage = image;
94 resizeImage(image: &visibleImage, newSize: size());
95
96 if (visibleImage.save(fileName, format: fileFormat)) {
97 modified = false;
98 return true;
99 }
100 return false;
101}
102//! [4]
103
104//! [5]
105void ScribbleArea::setPenColor(const QColor &newColor)
106//! [5] //! [6]
107{
108 myPenColor = newColor;
109}
110//! [6]
111
112//! [7]
113void ScribbleArea::setPenWidth(int newWidth)
114//! [7] //! [8]
115{
116 myPenWidth = newWidth;
117}
118//! [8]
119
120//! [9]
121void ScribbleArea::clearImage()
122//! [9] //! [10]
123{
124 image.fill(pixel: qRgb(r: 255, g: 255, b: 255));
125 modified = true;
126 update();
127}
128//! [10]
129
130//! [11]
131void ScribbleArea::mousePressEvent(QMouseEvent *event)
132//! [11] //! [12]
133{
134 if (event->button() == Qt::LeftButton) {
135 lastPoint = event->pos();
136 scribbling = true;
137 }
138}
139
140void ScribbleArea::mouseMoveEvent(QMouseEvent *event)
141{
142 if ((event->buttons() & Qt::LeftButton) && scribbling)
143 drawLineTo(endPoint: event->pos());
144}
145
146void ScribbleArea::mouseReleaseEvent(QMouseEvent *event)
147{
148 if (event->button() == Qt::LeftButton && scribbling) {
149 drawLineTo(endPoint: event->pos());
150 scribbling = false;
151 }
152}
153
154//! [12] //! [13]
155void ScribbleArea::paintEvent(QPaintEvent *event)
156//! [13] //! [14]
157{
158 QPainter painter(this);
159 QRect dirtyRect = event->rect();
160 painter.drawImage(targetRect: dirtyRect, image, sourceRect: dirtyRect);
161}
162//! [14]
163
164//! [15]
165void ScribbleArea::resizeEvent(QResizeEvent *event)
166//! [15] //! [16]
167{
168 if (width() > image.width() || height() > image.height()) {
169 int newWidth = qMax(a: width() + 128, b: image.width());
170 int newHeight = qMax(a: height() + 128, b: image.height());
171 resizeImage(image: &image, newSize: QSize(newWidth, newHeight));
172 update();
173 }
174 QWidget::resizeEvent(event);
175}
176//! [16]
177
178//! [17]
179void ScribbleArea::drawLineTo(const QPoint &endPoint)
180//! [17] //! [18]
181{
182 QPainter painter(&image);
183 painter.setPen(QPen(myPenColor, myPenWidth, Qt::SolidLine, Qt::RoundCap,
184 Qt::RoundJoin));
185 painter.drawLine(p1: lastPoint, p2: endPoint);
186 modified = true;
187
188 int rad = (myPenWidth / 2) + 2;
189 update(QRect(lastPoint, endPoint).normalized()
190 .adjusted(xp1: -rad, yp1: -rad, xp2: +rad, yp2: +rad));
191 lastPoint = endPoint;
192}
193//! [18]
194
195//! [19]
196void ScribbleArea::resizeImage(QImage *image, const QSize &newSize)
197//! [19] //! [20]
198{
199 if (image->size() == newSize)
200 return;
201
202 QImage newImage(newSize, QImage::Format_RGB32);
203 newImage.fill(pixel: qRgb(r: 255, g: 255, b: 255));
204 QPainter painter(&newImage);
205 painter.drawImage(p: QPoint(0, 0), image: *image);
206 *image = newImage;
207}
208//! [20]
209
210//! [21]
211void ScribbleArea::print()
212{
213#if defined(QT_PRINTSUPPORT_LIB) && QT_CONFIG(printdialog)
214 QPrinter printer(QPrinter::HighResolution);
215
216 QPrintDialog printDialog(&printer, this);
217//! [21] //! [22]
218 if (printDialog.exec() == QDialog::Accepted) {
219 QPainter painter(&printer);
220 QRect rect = painter.viewport();
221 QSize size = image.size();
222 size.scale(s: rect.size(), mode: Qt::KeepAspectRatio);
223 painter.setViewport(x: rect.x(), y: rect.y(), w: size.width(), h: size.height());
224 painter.setWindow(image.rect());
225 painter.drawImage(x: 0, y: 0, image);
226 }
227#endif // QT_CONFIG(printdialog)
228}
229//! [22]
230

source code of qtbase/examples/widgets/widgets/scribble/scribblearea.cpp